PageRenderTime 46ms CodeModel.GetById 19ms RepoModel.GetById 1ms app.codeStats 0ms

/wrfv2_fire/external/io_grib2/io_grib2.F

http://github.com/jbeezley/wrf-fire
FORTRAN Legacy | 4530 lines | 2683 code | 900 blank | 947 comment | 280 complexity | b4b51a64af2749be95dcb7ea22ea3fb5 MD5 | raw file
Possible License(s): AGPL-1.0
  1. !*-----------------------------------------------------------------------------
  2. !*
  3. !* Todd Hutchinson
  4. !* WSI
  5. !* 400 Minuteman Road
  6. !* Andover, MA 01810
  7. !* thutchinson@wsi.com
  8. !*
  9. !* August, 2005
  10. !*-----------------------------------------------------------------------------
  11. !*
  12. !* This io_grib2 API is designed to read WRF input and write WRF output data
  13. !* in grib version 2 format.
  14. !*
  15. #include "wrf_projection.h"
  16. module gr2_data_info
  17. !*
  18. !* This module will hold data internal to this I/O implementation.
  19. !* The variables will be accessible by all functions (provided they have a
  20. !* "USE gr2_data_info" line).
  21. !*
  22. USE grib2tbls_types
  23. integer , parameter :: FATAL = 1
  24. integer , parameter :: DEBUG = 100
  25. integer , parameter :: DateStrLen = 19
  26. integer , parameter :: maxMsgSize = 300
  27. integer , parameter :: firstFileHandle = 8
  28. integer , parameter :: maxFileHandles = 200
  29. integer , parameter :: maxLevels = 1000
  30. integer , parameter :: maxSoilLevels = 100
  31. integer , parameter :: maxDomains = 500
  32. character(200) :: mapfilename = 'grib2map.tbl'
  33. integer , parameter :: JIDSSIZE = 13
  34. integer , parameter :: JPDTSIZE = 15
  35. integer , parameter :: JGDTSIZE = 30
  36. logical :: grib2map_table_filled = .FALSE.
  37. logical :: WrfIOnotInitialized = .true.
  38. integer, dimension(maxDomains) :: domains
  39. integer :: max_domain = 0
  40. character*24 :: StartDate = ''
  41. character*24 :: InputProgramName = ''
  42. real :: timestep
  43. integer :: full_xsize, full_ysize
  44. REAL, dimension(maxSoilLevels) :: soil_depth, soil_thickness
  45. REAL, dimension(maxLevels) :: half_eta, full_eta
  46. integer :: wrf_projection
  47. integer :: background_proc_id
  48. integer :: forecast_proc_id
  49. integer :: production_status
  50. integer :: compression
  51. real :: center_lat, center_lon
  52. real :: dx,dy
  53. real :: truelat1, truelat2
  54. real :: proj_central_lon
  55. TYPE :: HandleVar
  56. character, dimension(:), pointer :: fileindex(:)
  57. integer :: CurrentTime
  58. integer :: NumberTimes
  59. integer :: sizeAllocated = 0
  60. logical :: write = .FALSE.
  61. character (DateStrLen), dimension(:),allocatable :: Times(:)
  62. logical :: committed, opened, used
  63. character*128 :: DataFile
  64. integer :: FileFd
  65. integer :: FileStatus
  66. integer :: recnum
  67. real :: last_scalar_time_written
  68. ENDTYPE
  69. TYPE (HandleVar), dimension(maxFileHandles),SAVE :: fileinfo
  70. character(len=30000), dimension(maxFileHandles) :: td_output
  71. character(len=30000), dimension(maxFileHandles) :: ti_output
  72. character(len=30000), dimension(maxFileHandles) :: scalar_output
  73. character(len=30000), dimension(maxFileHandles) :: global_input = ''
  74. character(len=30000), dimension(maxFileHandles) :: scalar_input = ''
  75. real :: last_fcst_secs
  76. real :: fcst_secs
  77. logical :: half_eta_init = .FALSE.
  78. logical :: full_eta_init = .FALSE.
  79. logical :: soil_thickness_init = .FALSE.
  80. logical :: soil_depth_init = .FALSE.
  81. end module gr2_data_info
  82. !*****************************************************************************
  83. subroutine ext_gr2_ioinit(SysDepInfo,Status)
  84. USE gr2_data_info
  85. implicit none
  86. #include "wrf_status_codes.h"
  87. #include "wrf_io_flags.h"
  88. CHARACTER*(*), INTENT(IN) :: SysDepInfo
  89. integer ,intent(out) :: Status
  90. integer :: i
  91. CHARACTER (LEN=300) :: wrf_err_message
  92. call wrf_debug ( DEBUG , 'Entering ext_gr2_ioinit')
  93. do i=firstFileHandle, maxFileHandles
  94. fileinfo(i)%used = .false.
  95. fileinfo(i)%committed = .false.
  96. fileinfo(i)%opened = .false.
  97. td_output(i) = ''
  98. ti_output(i) = ''
  99. scalar_output(i) = ''
  100. enddo
  101. domains(:) = -1
  102. last_fcst_secs = -1.0
  103. fileinfo(1:maxFileHandles)%FileStatus = WRF_FILE_NOT_OPENED
  104. WrfIOnotInitialized = .false.
  105. Status = WRF_NO_ERR
  106. return
  107. end subroutine ext_gr2_ioinit
  108. !*****************************************************************************
  109. subroutine ext_gr2_ioexit(Status)
  110. USE gr2_data_info
  111. implicit none
  112. #include "wrf_status_codes.h"
  113. integer ,intent(out) :: Status
  114. call wrf_debug ( DEBUG , 'Entering ext_gr2_ioexit')
  115. Status = WRF_NO_ERR
  116. if (grib2map_table_filled) then
  117. call free_grib2map()
  118. grib2map_table_filled = .FALSE.
  119. endif
  120. return
  121. end subroutine ext_gr2_ioexit
  122. !*****************************************************************************
  123. SUBROUTINE ext_gr2_open_for_read_begin ( FileName , Comm_compute, Comm_io, &
  124. SysDepInfo, DataHandle , Status )
  125. USE gr2_data_info
  126. USE grib2tbls_types
  127. USE grib_mod
  128. IMPLICIT NONE
  129. #include "wrf_status_codes.h"
  130. #include "wrf_io_flags.h"
  131. CHARACTER*(*) :: FileName
  132. INTEGER , INTENT(IN) :: Comm_compute , Comm_io
  133. CHARACTER*(*) :: SysDepInfo
  134. INTEGER , INTENT(OUT) :: DataHandle
  135. INTEGER , INTENT(OUT) :: Status
  136. CHARACTER (LEN=maxMsgSize) :: msg
  137. integer :: center, subcenter, MasterTblV, &
  138. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl
  139. integer :: fields_to_skip
  140. integer :: JIDS(JIDSSIZE), JPDTN, JPDT(JPDTSIZE), JGDTN, &
  141. JGDT(JGDTSIZE)
  142. logical :: UNPACK
  143. character*(100) :: VarName
  144. type(gribfield) :: gfld
  145. integer :: idx
  146. character(len=DateStrLen) :: theTime,refTime
  147. integer :: time_range_convert(13)
  148. integer :: fcstsecs
  149. integer :: endchar
  150. integer :: ierr
  151. INTERFACE
  152. Subroutine load_grib2map (filename, message, status)
  153. USE grib2tbls_types
  154. character*(*), intent(in) :: filename
  155. character*(*), intent(inout) :: message
  156. integer , intent(out) :: status
  157. END subroutine load_grib2map
  158. END INTERFACE
  159. call wrf_debug ( DEBUG , &
  160. 'Entering ext_gr2_open_for_read_begin, opening '//trim(FileName))
  161. CALL gr2_get_new_handle(DataHandle)
  162. !
  163. ! Open grib file
  164. !
  165. if (DataHandle .GT. 0) then
  166. call baopenr(DataHandle,trim(FileName),status)
  167. if (status .ne. 0) then
  168. Status = WRF_ERR_FATAL_BAD_FILE_STATUS
  169. else
  170. fileinfo(DataHandle)%opened = .true.
  171. fileinfo(DataHandle)%DataFile = TRIM(FileName)
  172. fileinfo(DataHandle)%FileStatus = WRF_FILE_OPENED_NOT_COMMITTED
  173. ! fileinfo(DataHandle)%CurrentTime = 1
  174. endif
  175. else
  176. Status = WRF_WARN_TOO_MANY_FILES
  177. return
  178. endif
  179. fileinfo(DataHandle)%recnum = -1
  180. !
  181. ! Fill up the grib2tbls structure from data in the grib2map file.
  182. !
  183. if (.NOT. grib2map_table_filled) then
  184. grib2map_table_filled = .TRUE.
  185. CALL load_grib2map(mapfilename, msg, status)
  186. if (status .ne. 0) then
  187. call wrf_message(trim(msg))
  188. Status = WRF_ERR_FATAL_BAD_FILE_STATUS
  189. return
  190. endif
  191. endif
  192. !
  193. ! Get the parameter info for metadata
  194. !
  195. VarName = "WRF_GLOBAL"
  196. CALL get_parminfo(VarName, center, subcenter, MasterTblV, &
  197. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl, status)
  198. if (status .ne. 0) then
  199. write(msg,*) 'Could not find parameter for '// &
  200. trim(VarName)//' Skipping output of '//trim(VarName)
  201. call wrf_message(trim(msg))
  202. Status = WRF_GRIB2_ERR_GRIB2MAP
  203. return
  204. endif
  205. !
  206. ! Read the metadata
  207. !
  208. fields_to_skip = 0
  209. !
  210. ! First, set all values to the wildcard, then reset values that we wish
  211. ! to specify.
  212. !
  213. call gr2_g2lib_wildcard(JIDS, JPDT, JGDT)
  214. JIDS(1) = center
  215. JIDS(2) = subcenter
  216. JIDS(3) = MasterTblV
  217. JIDS(4) = LocalTblV
  218. JIDS(5) = 1 ! Indicates that time is "Start of Forecast"
  219. JIDS(13) = 1 ! Type of processed data (1 for forecast products)
  220. JPDTN = 0 ! Product definition template number
  221. JPDT(1) = Category
  222. JPDT(2) = ParmNum
  223. JPDT(3) = 2 ! Generating process id
  224. JPDT(9) = 0 ! Forecast time
  225. JGDTN = -1 ! Indicates that any Grid Display Template is a match
  226. UNPACK = .FALSE. ! Dont unpack bitmap and data values
  227. CALL GETGB2(DataHandle, DataHandle, fields_to_skip, -1, Disc, JIDS, JPDTN, &
  228. JPDT, JGDTN, JGDT, UNPACK, fileinfo(DataHandle)%recnum, gfld, status)
  229. if (status .ne. 0) then
  230. if (status .eq. 99) then
  231. write(msg,*)'Could not find metadata field named '//trim(VarName)
  232. else
  233. write(msg,*)'Retrieving grib field '//trim(VarName)//' failed, ',status
  234. endif
  235. call wrf_message(trim(msg))
  236. status = WRF_GRIB2_ERR_GETGB2
  237. return
  238. endif
  239. global_input(DataHandle) = transfer(gfld%local,global_input(DataHandle))
  240. global_input(DataHandle)(gfld%locallen+1:30000) = ' '
  241. call gf_free(gfld)
  242. !
  243. ! Read and index all scalar data
  244. !
  245. VarName = "WRF_SCALAR"
  246. CALL get_parminfo(VarName, center, subcenter, MasterTblV, &
  247. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl, status)
  248. if (status .ne. 0) then
  249. write(msg,*) 'Could not find parameter for '// &
  250. trim(VarName)//' Skipping reading of '//trim(VarName)
  251. call wrf_message(trim(msg))
  252. Status = WRF_GRIB2_ERR_GRIB2MAP
  253. return
  254. endif
  255. !
  256. ! Read the metadata
  257. !
  258. ! First, set all values to wild, then specify necessary values
  259. !
  260. call gr2_g2lib_wildcard(JIDS, JPDT, JGDT)
  261. JIDS(1) = center
  262. JIDS(2) = subcenter
  263. JIDS(3) = MasterTblV
  264. JIDS(4) = LocalTblV
  265. JIDS(5) = 1 ! Indicates that time is "Start of Forecast"
  266. JIDS(13) = 1 ! Type of processed data (1 for forecast products)
  267. JPDTN = 0 ! Product definition template number
  268. JPDT(1) = Category
  269. JPDT(2) = ParmNum
  270. JPDT(3) = 2 ! Generating process id
  271. JGDTN = -1 ! Indicates that any Grid Display Template is a match
  272. UNPACK = .FALSE. ! Dont unpack bitmap and data values
  273. fields_to_skip = 0
  274. do while (status .eq. 0)
  275. CALL GETGB2(DataHandle, 0, fields_to_skip, -1, -1, JIDS, JPDTN, &
  276. JPDT, JGDTN, JGDT, UNPACK, fileinfo(DataHandle)%recnum, &
  277. gfld, status)
  278. if (status .eq. 99) then
  279. exit
  280. else if (status .ne. 0) then
  281. write(msg,*)'Finding data field '//trim(VarName)//' failed 1.'
  282. call wrf_message(trim(msg))
  283. Status = WRF_GRIB2_ERR_READ
  284. return
  285. endif
  286. ! Build times list here
  287. write(refTime,'(I4,A,I2.2,A,I2.2,A,I2.2,A,I2.2,A,I2.2)') &
  288. gfld%idsect(6),'-',gfld%idsect(7),'-',gfld%idsect(8),'_',&
  289. gfld%idsect(9),':',gfld%idsect(10),':',gfld%idsect(11)
  290. time_range_convert(:) = -1
  291. time_range_convert(1) = 60
  292. time_range_convert(2) = 60*60
  293. time_range_convert(3) = 24*60*60
  294. time_range_convert(10) = 3*60*60
  295. time_range_convert(11) = 6*60*60
  296. time_range_convert(12) = 12*60*60
  297. time_range_convert(13) = 1
  298. if (time_range_convert(gfld%ipdtmpl(8)) .gt. 0) then
  299. fcstsecs = gfld%ipdtmpl(9)*time_range_convert(gfld%ipdtmpl(8))
  300. else
  301. write(msg,*)'Invalid time range in input data: ',gfld%ipdtmpl(8),&
  302. ' Skipping'
  303. call wrf_message(trim(msg))
  304. call gf_free(gfld)
  305. cycle
  306. endif
  307. call advance_wrf_time(refTime,fcstsecs,theTime)
  308. call gr2_add_time(DataHandle,theTime)
  309. fields_to_skip = fields_to_skip + fileinfo(DataHandle)%recnum
  310. scalar_input(DataHandle) = transfer(gfld%local,scalar_input(DataHandle))
  311. scalar_input(DataHandle)(gfld%locallen+1:30000) = ' '
  312. call gf_free(gfld)
  313. enddo
  314. !
  315. ! Fill up the eta levels variables
  316. !
  317. if (.not. full_eta_init) then
  318. CALL gr2_fill_levels(DataHandle, "ZNW", full_eta, ierr)
  319. if (ierr .eq. 0) then
  320. full_eta_init = .TRUE.
  321. endif
  322. endif
  323. if (.not. half_eta_init) then
  324. CALL gr2_fill_levels(DataHandle, "ZNU", half_eta, ierr)
  325. if (ierr .eq. 0) then
  326. half_eta_init = .TRUE.
  327. endif
  328. endif
  329. !
  330. ! Fill up the soil levels
  331. !
  332. if (.not. soil_depth_init) then
  333. call gr2_fill_levels(DataHandle,"ZS",soil_depth, ierr)
  334. if (ierr .eq. 0) then
  335. soil_depth_init = .TRUE.
  336. endif
  337. endif
  338. if (.not. soil_thickness_init) then
  339. call gr2_fill_levels(DataHandle,"DZS",soil_thickness, ierr)
  340. if (ierr .eq. 0) then
  341. soil_thickness_init = .TRUE.
  342. endif
  343. endif
  344. !
  345. ! Fill up any variables from the global metadata
  346. !
  347. CALL gr2_get_metadata_value(global_input(DataHandle), &
  348. 'START_DATE', StartDate, status)
  349. if (status .ne. 0) then
  350. write(msg,*)'Could not find metadata value for START_DATE, continuing'
  351. call wrf_message(trim(msg))
  352. endif
  353. CALL gr2_get_metadata_value(global_input(DataHandle), &
  354. 'PROGRAM_NAME', InputProgramName, status)
  355. if (status .ne. 0) then
  356. write(msg,*)'Could not find metadata value for PROGRAM_NAME, continuing'
  357. call wrf_message(trim(msg))
  358. else
  359. endchar = SCAN(InputProgramName," ")
  360. InputProgramName = InputProgramName(1:endchar)
  361. endif
  362. Status = WRF_NO_ERR
  363. call wrf_debug ( DEBUG , 'Exiting ext_gr2_open_for_read_begin')
  364. RETURN
  365. END SUBROUTINE ext_gr2_open_for_read_begin
  366. !*****************************************************************************
  367. SUBROUTINE ext_gr2_open_for_read_commit( DataHandle , Status )
  368. USE gr2_data_info
  369. IMPLICIT NONE
  370. #include "wrf_status_codes.h"
  371. #include "wrf_io_flags.h"
  372. character(len=maxMsgSize) :: msg
  373. INTEGER , INTENT(IN ) :: DataHandle
  374. INTEGER , INTENT(OUT) :: Status
  375. call wrf_debug ( DEBUG , 'Entering ext_gr2_open_for_read_commit')
  376. Status = WRF_NO_ERR
  377. if(WrfIOnotInitialized) then
  378. Status = WRF_IO_NOT_INITIALIZED
  379. write(msg,*) 'ext_gr2_ioinit was not called ',__FILE__,', line', __LINE__
  380. call wrf_debug ( FATAL , msg)
  381. return
  382. endif
  383. fileinfo(DataHandle)%committed = .true.
  384. fileinfo(DataHandle)%FileStatus = WRF_FILE_OPENED_FOR_READ
  385. Status = WRF_NO_ERR
  386. RETURN
  387. END SUBROUTINE ext_gr2_open_for_read_commit
  388. !*****************************************************************************
  389. SUBROUTINE ext_gr2_open_for_read ( FileName , Comm_compute, Comm_io, &
  390. SysDepInfo, DataHandle , Status )
  391. USE gr2_data_info
  392. IMPLICIT NONE
  393. #include "wrf_status_codes.h"
  394. CHARACTER*(*) :: FileName
  395. INTEGER , INTENT(IN) :: Comm_compute , Comm_io
  396. CHARACTER*(*) :: SysDepInfo
  397. INTEGER , INTENT(OUT) :: DataHandle
  398. INTEGER , INTENT(OUT) :: Status
  399. call wrf_debug ( DEBUG , 'Entering ext_gr2_open_for_read')
  400. DataHandle = 0 ! dummy setting to quiet warning message
  401. CALL ext_gr2_open_for_read_begin( FileName, Comm_compute, Comm_io, &
  402. SysDepInfo, DataHandle, Status )
  403. IF ( Status .EQ. WRF_NO_ERR ) THEN
  404. CALL ext_gr2_open_for_read_commit( DataHandle, Status )
  405. ENDIF
  406. return
  407. RETURN
  408. END SUBROUTINE ext_gr2_open_for_read
  409. !*****************************************************************************
  410. SUBROUTINE ext_gr2_open_for_write_begin(FileName, Comm, IOComm, SysDepInfo, &
  411. DataHandle, Status)
  412. USE gr2_data_info
  413. implicit none
  414. #include "wrf_status_codes.h"
  415. #include "wrf_io_flags.h"
  416. character*(*) ,intent(in) :: FileName
  417. integer ,intent(in) :: Comm
  418. integer ,intent(in) :: IOComm
  419. character*(*) ,intent(in) :: SysDepInfo
  420. integer ,intent(out) :: DataHandle
  421. integer ,intent(out) :: Status
  422. integer :: ierr
  423. CHARACTER (LEN=maxMsgSize) :: msg
  424. INTERFACE
  425. Subroutine load_grib2map (filename, message, status)
  426. USE grib2tbls_types
  427. character*(*), intent(in) :: filename
  428. character*(*), intent(inout) :: message
  429. integer , intent(out) :: status
  430. END subroutine load_grib2map
  431. END INTERFACE
  432. call wrf_debug ( DEBUG , 'Entering ext_gr2_open_for_write_begin')
  433. Status = WRF_NO_ERR
  434. if (.NOT. grib2map_table_filled) then
  435. grib2map_table_filled = .TRUE.
  436. CALL load_grib2map(mapfilename, msg, status)
  437. if (status .ne. 0) then
  438. call wrf_message(trim(msg))
  439. Status = WRF_ERR_FATAL_BAD_FILE_STATUS
  440. return
  441. endif
  442. endif
  443. CALL gr2_get_new_handle(DataHandle)
  444. if (DataHandle .GT. 0) then
  445. call baopenw(DataHandle,trim(FileName),ierr)
  446. if (ierr .ne. 0) then
  447. Status = WRF_ERR_FATAL_BAD_FILE_STATUS
  448. else
  449. fileinfo(DataHandle)%opened = .true.
  450. fileinfo(DataHandle)%DataFile = TRIM(FileName)
  451. fileinfo(DataHandle)%FileStatus = WRF_FILE_OPENED_NOT_COMMITTED
  452. endif
  453. fileinfo(DataHandle)%last_scalar_time_written = -1
  454. fileinfo(DataHandle)%committed = .false.
  455. td_output(DataHandle) = ''
  456. ti_output(DataHandle) = ''
  457. scalar_output(DataHandle) = ''
  458. fileinfo(DataHandle)%write = .true.
  459. else
  460. Status = WRF_WARN_TOO_MANY_FILES
  461. endif
  462. RETURN
  463. END SUBROUTINE ext_gr2_open_for_write_begin
  464. !*****************************************************************************
  465. SUBROUTINE ext_gr2_open_for_write_commit( DataHandle , Status )
  466. USE gr2_data_info
  467. IMPLICIT NONE
  468. #include "wrf_status_codes.h"
  469. #include "wrf_io_flags.h"
  470. INTEGER , INTENT(IN ) :: DataHandle
  471. INTEGER , INTENT(OUT) :: Status
  472. call wrf_debug ( DEBUG , 'Entering ext_gr2_open_for_write_commit')
  473. IF ( fileinfo(DataHandle)%opened ) THEN
  474. IF ( fileinfo(DataHandle)%used ) THEN
  475. fileinfo(DataHandle)%committed = .true.
  476. fileinfo(DataHandle)%FileStatus = WRF_FILE_OPENED_FOR_WRITE
  477. ENDIF
  478. ENDIF
  479. Status = WRF_NO_ERR
  480. RETURN
  481. END SUBROUTINE ext_gr2_open_for_write_commit
  482. !*****************************************************************************
  483. subroutine ext_gr2_inquiry (Inquiry, Result, Status)
  484. use gr2_data_info
  485. implicit none
  486. #include "wrf_status_codes.h"
  487. character *(*), INTENT(IN) :: Inquiry
  488. character *(*), INTENT(OUT) :: Result
  489. integer ,INTENT(INOUT) :: Status
  490. SELECT CASE (Inquiry)
  491. CASE ("RANDOM_WRITE","RANDOM_READ")
  492. Result='ALLOW'
  493. CASE ("SEQUENTIAL_WRITE","SEQUENTIAL_READ")
  494. Result='NO'
  495. CASE ("OPEN_READ", "OPEN_WRITE", "OPEN_COMMIT_WRITE")
  496. Result='REQUIRE'
  497. CASE ("OPEN_COMMIT_READ","PARALLEL_IO")
  498. Result='NO'
  499. CASE ("SELF_DESCRIBING","SUPPORT_METADATA","SUPPORT_3D_FIELDS")
  500. Result='YES'
  501. CASE ("MEDIUM")
  502. Result ='FILE'
  503. CASE DEFAULT
  504. Result = 'No Result for that inquiry!'
  505. END SELECT
  506. Status=WRF_NO_ERR
  507. return
  508. end subroutine ext_gr2_inquiry
  509. !*****************************************************************************
  510. SUBROUTINE ext_gr2_inquire_opened ( DataHandle, FileName , FileStat, Status )
  511. USE gr2_data_info
  512. IMPLICIT NONE
  513. #include "wrf_status_codes.h"
  514. #include "wrf_io_flags.h"
  515. INTEGER , INTENT(IN) :: DataHandle
  516. CHARACTER*(*) :: FileName
  517. INTEGER , INTENT(OUT) :: FileStat
  518. INTEGER , INTENT(OUT) :: Status
  519. call wrf_debug ( DEBUG , 'Entering ext_gr2_inquire_opened')
  520. FileStat = WRF_NO_ERR
  521. if ((DataHandle .ge. firstFileHandle) .and. &
  522. (DataHandle .le. maxFileHandles)) then
  523. FileStat = fileinfo(DataHandle)%FileStatus
  524. else
  525. FileStat = WRF_FILE_NOT_OPENED
  526. endif
  527. Status = FileStat
  528. RETURN
  529. END SUBROUTINE ext_gr2_inquire_opened
  530. !*****************************************************************************
  531. SUBROUTINE ext_gr2_ioclose ( DataHandle, Status )
  532. USE gr2_data_info
  533. IMPLICIT NONE
  534. #include "wrf_status_codes.h"
  535. #include "wrf_io_flags.h"
  536. INTEGER DataHandle, Status
  537. INTEGER istat
  538. character(len=1000) :: outstring
  539. character :: lf
  540. character*(maxMsgSize) :: msg
  541. integer :: idx
  542. lf=char(10)
  543. call wrf_debug ( DEBUG , 'Entering ext_gr2_ioclose')
  544. Status = WRF_NO_ERR
  545. if (fileinfo(DataHandle)%write .eqv. .TRUE.) then
  546. call gr2_fill_local_use(DataHandle,scalar_output(DataHandle),&
  547. "WRF_SCALAR",fcst_secs,msg,status)
  548. if (status .ne. 0) then
  549. call wrf_message(trim(msg))
  550. return
  551. endif
  552. fileinfo(DataHandle)%last_scalar_time_written = fcst_secs
  553. scalar_output(DataHandle) = ''
  554. call gr2_fill_local_use(DataHandle,&
  555. trim(ti_output(DataHandle))//trim(td_output(DataHandle)),&
  556. "WRF_GLOBAL",0,msg,status)
  557. if (status .ne. 0) then
  558. call wrf_message(trim(msg))
  559. return
  560. endif
  561. ti_output(DataHandle) = ''
  562. td_output(DataHandle) = ''
  563. endif
  564. do idx = 1,fileinfo(DataHandle)%NumberTimes
  565. if (allocated(fileinfo(DataHandle)%Times)) then
  566. deallocate(fileinfo(DataHandle)%Times)
  567. endif
  568. enddo
  569. fileinfo(DataHandle)%NumberTimes = 0
  570. fileinfo(DataHandle)%sizeAllocated = 0
  571. fileinfo(DataHandle)%CurrentTime = 0
  572. fileinfo(DataHandle)%write = .FALSE.
  573. call baclose(DataHandle,status)
  574. if (status .ne. 0) then
  575. call wrf_message("Closing file failed, continuing")
  576. else
  577. fileinfo(DataHandle)%opened = .true.
  578. fileinfo(DataHandle)%DataFile = ''
  579. fileinfo(DataHandle)%FileStatus = WRF_FILE_NOT_OPENED
  580. endif
  581. fileinfo(DataHandle)%used = .false.
  582. RETURN
  583. END SUBROUTINE ext_gr2_ioclose
  584. !*****************************************************************************
  585. SUBROUTINE ext_gr2_write_field( DataHandle , DateStrIn , VarName , &
  586. Field , FieldType , Comm , IOComm, &
  587. DomainDesc , MemoryOrder , Stagger , &
  588. DimNames , &
  589. DomainStart , DomainEnd , &
  590. MemoryStart , MemoryEnd , &
  591. PatchStart , PatchEnd , &
  592. Status )
  593. USE gr2_data_info
  594. USE grib2tbls_types
  595. IMPLICIT NONE
  596. #include "wrf_status_codes.h"
  597. #include "wrf_io_flags.h"
  598. integer ,intent(in) :: DataHandle
  599. character*(*) ,intent(in) :: DateStrIn
  600. character*(*) ,intent(in) :: VarName
  601. integer ,intent(in) :: FieldType
  602. integer ,intent(inout) :: Comm
  603. integer ,intent(inout) :: IOComm
  604. integer ,intent(in) :: DomainDesc
  605. character*(*) ,intent(in) :: MemoryOrder
  606. character*(*) ,intent(in) :: Stagger
  607. character*(*) , dimension (*) ,intent(in) :: DimNames
  608. integer ,dimension(*) ,intent(in) :: DomainStart, DomainEnd
  609. integer ,dimension(*) ,intent(in) :: MemoryStart, MemoryEnd
  610. integer ,dimension(*) ,intent(in) :: PatchStart, PatchEnd
  611. integer ,intent(out) :: Status
  612. real , intent(in), &
  613. dimension( 1:1,MemoryStart(1):MemoryEnd(1), &
  614. MemoryStart(2):MemoryEnd(2), &
  615. MemoryStart(3):MemoryEnd(3) ) :: Field
  616. character (120) :: DateStr
  617. character (maxMsgSize) :: msg
  618. integer :: xsize, ysize, zsize
  619. integer :: x, y, z
  620. integer :: &
  621. x_start,x_end,y_start,y_end,z_start,z_end
  622. integer :: idx
  623. integer :: proj_center_flag
  624. logical :: vert_stag = .false.
  625. real, dimension(:,:), pointer :: data
  626. integer :: istat
  627. integer :: accum_period
  628. integer, dimension(maxLevels) :: level1, level2
  629. integer, dimension(maxLevels) :: grib_levels
  630. logical :: soil_layers, fraction
  631. integer :: vert_unit1, vert_unit2
  632. integer :: vert_sclFctr1, vert_sclFctr2
  633. integer :: this_domain
  634. logical :: new_domain
  635. real :: &
  636. region_center_lat, region_center_lon
  637. integer :: dom_xsize, dom_ysize;
  638. integer , parameter :: lcgrib = 2000000
  639. character (lcgrib) :: cgrib
  640. integer :: ierr
  641. integer :: lengrib
  642. integer :: center, subcenter, &
  643. MasterTblV, LocalTblV, Disc, Category, ParmNum, DecScl, BinScl
  644. CHARACTER(len=100) :: tmpstr
  645. integer :: ndims
  646. integer :: dim1size, dim2size, dim3size, dim3
  647. integer :: numlevels
  648. integer :: ngrdpts
  649. integer :: bytes_written
  650. call wrf_debug ( DEBUG , 'Entering ext_gr2_write_field for parameter '//&
  651. VarName)
  652. !
  653. ! If DateStr is all 0s, we reset it to StartDate. For some reason,
  654. ! in idealized simulations, StartDate is 0001-01-01_00:00:00 while
  655. ! the first DateStr is 0000-00-00_00:00:00.
  656. !
  657. if (DateStrIn .eq. '0000-00-00_00:00:00') then
  658. DateStr = TRIM(StartDate)
  659. else
  660. DateStr = DateStrIn
  661. endif
  662. !
  663. ! Check if this is a domain that we haven t seen yet. If so, add it to
  664. ! the list of domains.
  665. !
  666. this_domain = 0
  667. new_domain = .false.
  668. do idx = 1, max_domain
  669. if (DomainDesc .eq. domains(idx)) then
  670. this_domain = idx
  671. endif
  672. enddo
  673. if (this_domain .eq. 0) then
  674. max_domain = max_domain + 1
  675. domains(max_domain) = DomainDesc
  676. this_domain = max_domain
  677. new_domain = .true.
  678. endif
  679. zsize = 1
  680. xsize = 1
  681. ysize = 1
  682. soil_layers = .false.
  683. fraction = .false.
  684. ! First, handle then special cases for the boundary data.
  685. CALL get_dims(MemoryOrder, PatchStart, PatchEnd, ndims, x_start, x_end, &
  686. y_start, y_end,z_start,z_end)
  687. xsize = x_end - x_start + 1
  688. ysize = y_end - y_start + 1
  689. zsize = z_end - z_start + 1
  690. do idx = 1, len(MemoryOrder)
  691. if ((MemoryOrder(idx:idx) .eq. 'Z') .and. &
  692. (DimNames(idx) .eq. 'soil_layers_stag')) then
  693. soil_layers = .true.
  694. else if ((VarName .eq. 'LANDUSEF') .or. (VarName .eq. 'SOILCBOT') .or. &
  695. (VarName .eq. 'SOILCTOP')) then
  696. fraction = .true.
  697. endif
  698. enddo
  699. if (zsize .eq. 0) then
  700. zsize = 1
  701. endif
  702. !
  703. ! Fill up the variables that hold the vertical coordinate data
  704. !
  705. if (VarName .eq. 'ZNU') then
  706. do idx = 1, zsize
  707. half_eta(idx) = Field(1,idx,1,1)
  708. enddo
  709. half_eta_init = .TRUE.
  710. endif
  711. if (VarName .eq. 'ZNW') then
  712. do idx = 1, zsize
  713. full_eta(idx) = Field(1,idx,1,1)
  714. enddo
  715. full_eta_init = .TRUE.
  716. endif
  717. if (VarName .eq. 'ZS') then
  718. do idx = 1, zsize
  719. soil_depth(idx) = Field(1,idx,1,1)
  720. enddo
  721. soil_depth_init = .TRUE.
  722. endif
  723. if (VarName .eq. 'DZS') then
  724. do idx = 1, zsize
  725. soil_thickness(idx) = Field(1,idx,1,1)
  726. enddo
  727. soil_thickness_init = .TRUE.
  728. endif
  729. !
  730. ! Check to assure that dimensions are valid
  731. !
  732. if ((xsize .lt. 1) .or. (ysize .lt. 1) .or. (zsize .lt. 1)) then
  733. write(msg,*) 'Cannot output field with memory order: ', &
  734. MemoryOrder,Varname
  735. call wrf_message(trim(msg))
  736. return
  737. endif
  738. if (fileinfo(DataHandle)%opened .and. fileinfo(DataHandle)%committed) then
  739. if (StartDate == '') then
  740. StartDate = DateStr
  741. endif
  742. CALL geth_idts(DateStr,StartDate,fcst_secs)
  743. !
  744. ! If this is a new forecast time, and we have not written the
  745. ! last_fcst_secs scalar output yet, then write it here.
  746. !
  747. if ((abs(fcst_secs - 0.0) .gt. 0.01) .and. &
  748. (last_fcst_secs .ge. 0) .and. &
  749. (abs(fcst_secs - last_fcst_secs) .gt. 0.01) .and. &
  750. (abs(last_fcst_secs - fileinfo(DataHandle)%last_scalar_time_written) .gt. 0.01) ) then
  751. call gr2_fill_local_use(DataHandle,scalar_output(DataHandle),&
  752. "WRF_SCALAR",last_fcst_secs,msg,status)
  753. if (status .ne. 0) then
  754. call wrf_message(trim(msg))
  755. return
  756. endif
  757. fileinfo(DataHandle)%last_scalar_time_written = last_fcst_secs
  758. scalar_output(DataHandle) = ''
  759. endif
  760. call get_vert_stag(VarName,Stagger,vert_stag)
  761. do idx = 1, zsize
  762. call gr2_get_levels(VarName, idx, zsize, soil_layers, vert_stag, &
  763. fraction, vert_unit1, vert_unit2, vert_sclFctr1, &
  764. vert_sclFctr2, level1(idx), level2(idx))
  765. enddo
  766. !
  767. ! Get the center lat/lon for the area being output. For some cases (such
  768. ! as for boundary areas, the center of the area is different from the
  769. ! center of the model grid.
  770. !
  771. if (index(Stagger,'X') .le. 0) then
  772. dom_xsize = full_xsize - 1
  773. else
  774. dom_xsize = full_xsize
  775. endif
  776. if (index(Stagger,'Y') .le. 0) then
  777. dom_ysize = full_ysize - 1
  778. else
  779. dom_ysize = full_ysize
  780. endif
  781. CALL get_region_center(MemoryOrder, wrf_projection, center_lat, &
  782. center_lon, dom_xsize, dom_ysize, dx, dy, proj_central_lon, &
  783. proj_center_flag, truelat1, truelat2, xsize, ysize, &
  784. region_center_lat, region_center_lon)
  785. if (ndims .eq. 0) then ! Scalar quantity
  786. ALLOCATE(data(1:1,1:1), STAT=istat)
  787. call gr2_retrieve_data(MemoryOrder, MemoryStart, MemoryEnd, &
  788. xsize, ysize, zsize, z, FieldType, Field, data)
  789. write(tmpstr,'(G17.10)')data(1,1)
  790. CALL gr2_build_string (scalar_output(DataHandle), &
  791. trim(adjustl(VarName)), tmpstr, 1, Status)
  792. DEALLOCATE(data)
  793. else if (ndims .ge. 1) then ! Vector (1-D) and 2/3 D quantities
  794. if (ndims .eq. 1) then ! Handle Vector (1-D) parameters
  795. dim1size = zsize
  796. dim2size = 1
  797. dim3size = 1
  798. else ! Handle 2/3 D parameters
  799. dim1size = xsize
  800. dim2size = ysize
  801. dim3size = zsize
  802. endif
  803. ALLOCATE(data(1:dim1size,1:dim2size), STAT=istat)
  804. CALL get_parminfo(VarName, center, subcenter, MasterTblV, &
  805. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl, status)
  806. if (status .ne. 0) then
  807. write(msg,*) 'Could not find parameter for '// &
  808. trim(VarName)//' Skipping output of '//trim(VarName)
  809. call wrf_message(trim(msg))
  810. Status = WRF_GRIB2_ERR_GRIB2MAP
  811. return
  812. endif
  813. VERTDIM : do dim3 = 1, dim3size
  814. call gr2_retrieve_data(MemoryOrder, MemoryStart, MemoryEnd, xsize, &
  815. ysize, zsize, dim3, FieldType, Field, data)
  816. !
  817. ! Here, we do any necessary conversions to the data.
  818. !
  819. ! Potential temperature is sometimes passed in as perturbation
  820. ! potential temperature (i.e., POT-300). Other times (i.e., from
  821. ! WRF SI), it is passed in as full potential temperature.
  822. ! Here, we convert to full potential temperature by adding 300
  823. ! only if POT < 200 K.
  824. !
  825. if (VarName == 'T') then
  826. if ((data(1,1) < 200) .and. (data(1,1) .ne. 0)) then
  827. data = data + 300
  828. endif
  829. endif
  830. !
  831. ! For precip, we setup the accumulation period, and output a precip
  832. ! rate for time-step precip.
  833. !
  834. if ((VarName .eq. 'RAINCV') .or. (VarName .eq. 'RAINNCV')) then
  835. ! Convert time-step precip to precip rate.
  836. data = data/timestep
  837. accum_period = 0
  838. else
  839. accum_period = 0
  840. endif
  841. !
  842. ! Create indicator and identification sections (sections 0 and 1)
  843. !
  844. CALL gr2_create_w(StartDate, cgrib, lcgrib, production_status, &
  845. Disc, center, subcenter, MasterTblV, LocalTblV, ierr, msg)
  846. if (ierr .ne. 0) then
  847. call wrf_message(trim(msg))
  848. Status = WRF_GRIB2_ERR_GRIBCREATE
  849. return
  850. endif
  851. !
  852. ! Add the grid definition section (section 3) using a 1x1 grid
  853. !
  854. call gr2_addgrid_w(cgrib, lcgrib, center_lat, proj_central_lon, &
  855. wrf_projection, truelat1, truelat2, xsize, ysize, dx, dy, &
  856. region_center_lat, region_center_lon, ierr, msg)
  857. if (ierr .ne. 0) then
  858. call wrf_message(trim(msg))
  859. Status = WRF_GRIB2_ERR_ADDGRIB
  860. return
  861. endif
  862. if (ndims .eq. 1) then
  863. numlevels = zsize
  864. grib_levels(:) = level1(:)
  865. ngrdpts = zsize
  866. else
  867. numlevels = 2
  868. grib_levels(1) = level1(dim3)
  869. grib_levels(2) = level2(dim3)
  870. ngrdpts = xsize*ysize
  871. endif
  872. !
  873. ! Add the Product Definition, Data representation, bitmap
  874. ! and data sections (sections 4-7)
  875. !
  876. call gr2_addfield_w(cgrib, lcgrib, VarName, Category, ParmNum, &
  877. DecScl, BinScl, fcst_secs, vert_unit1, vert_unit2, &
  878. vert_sclFctr1, vert_sclFctr2, numlevels, &
  879. grib_levels, ngrdpts, background_proc_id, forecast_proc_id, &
  880. compression, data, ierr, msg)
  881. if (ierr .eq. 11) then
  882. write(msg,'(A,I7,A)') 'WARNING: decimal scale for field '//&
  883. trim(VarName)//' at level ',grib_levels(1),&
  884. ' was reduced to fit field into 24 bits. '//&
  885. ' Some precision may be lost!'//&
  886. ' To prevent this message, reduce decimal scale '//&
  887. 'factor in '//trim(mapfilename)
  888. call wrf_message(trim(msg))
  889. else if (ierr .eq. 12) then
  890. write(msg,'(A,I7,A)') 'WARNING: binary scale for field '//&
  891. trim(VarName)//' at level ',grib_levels(1), &
  892. ' was reduced to fit field into 24 bits. '//&
  893. ' Some precision may be lost!'//&
  894. ' To prevent this message, reduce binary scale '//&
  895. 'factor in '//trim(mapfilename)
  896. call wrf_message(trim(msg))
  897. else if (ierr .ne. 0) then
  898. call wrf_message(trim(msg))
  899. Status = WRF_GRIB2_ERR_ADDFIELD
  900. return
  901. endif
  902. !
  903. ! Close out the message
  904. !
  905. call gribend(cgrib,lcgrib,lengrib,ierr)
  906. if (ierr .ne. 0) then
  907. write(msg,*) 'gribend failed with ierr: ',ierr
  908. call wrf_message(trim(msg))
  909. Status = WRF_GRIB2_ERR_GRIBEND
  910. return
  911. endif
  912. !
  913. ! Write the data to the file
  914. !
  915. ! call write_file_n(fileinfo(DataHandle)%FileFd, cgrib, lengrib, ierr)
  916. call bawrite(DataHandle, -1, lengrib, bytes_written, cgrib)
  917. if (bytes_written .ne. lengrib) then
  918. write(msg,*) '1 Error writing cgrib to file, wrote: ', &
  919. bytes_written, ' bytes. Tried to write ', lengrib, ' bytes'
  920. call wrf_message(trim(msg))
  921. Status = WRF_GRIB2_ERR_WRITE
  922. return
  923. endif
  924. ENDDO VERTDIM
  925. DEALLOCATE(data)
  926. endif
  927. last_fcst_secs = fcst_secs
  928. endif
  929. deallocate(data, STAT = istat)
  930. Status = WRF_NO_ERR
  931. call wrf_debug ( DEBUG , 'Leaving ext_gr2_write_field')
  932. RETURN
  933. END SUBROUTINE ext_gr2_write_field
  934. !*****************************************************************************
  935. SUBROUTINE ext_gr2_read_field ( DataHandle , DateStr , VarName , Field , &
  936. FieldType , Comm , IOComm, DomainDesc , MemoryOrder , Stagger , &
  937. DimNames , DomainStart , DomainEnd , MemoryStart , MemoryEnd , &
  938. PatchStart , PatchEnd , Status )
  939. USE gr2_data_info
  940. USE grib_mod
  941. IMPLICIT NONE
  942. #include "wrf_status_codes.h"
  943. #include "wrf_io_flags.h"
  944. INTEGER ,intent(in) :: DataHandle
  945. CHARACTER*(*) ,intent(in) :: DateStr
  946. CHARACTER*(*) ,intent(in) :: VarName
  947. integer ,intent(inout) :: FieldType
  948. integer ,intent(inout) :: Comm
  949. integer ,intent(inout) :: IOComm
  950. integer ,intent(inout) :: DomainDesc
  951. character*(*) ,intent(inout) :: MemoryOrder
  952. character*(*) ,intent(inout) :: Stagger
  953. character*(*) , dimension (*) ,intent(inout) :: DimNames
  954. integer ,dimension(*) ,intent(inout) :: DomainStart, DomainEnd
  955. integer ,dimension(*) ,intent(inout) :: MemoryStart, MemoryEnd
  956. integer ,dimension(*) ,intent(inout) :: PatchStart, PatchEnd
  957. integer ,intent(out) :: Status
  958. INTEGER ,intent(out) :: Field(*)
  959. integer :: xsize,ysize,zsize
  960. integer :: x_start,x_end,y_start,y_end,z_start,z_end
  961. integer :: ndims
  962. character (len=1000) :: Value
  963. character (maxMsgSize) :: msg
  964. integer :: ierr
  965. real :: Data
  966. integer :: center, subcenter, MasterTblV, &
  967. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl
  968. integer :: dim1size,dim2size,dim3size,dim3
  969. integer :: idx
  970. integer :: fields_to_skip
  971. integer :: JIDS(JIDSSIZE), JPDTN, JPDT(JPDTSIZE), JGDTN, &
  972. JGDT(JGDTSIZE)
  973. logical :: UNPACK
  974. type(gribfield) :: gfld
  975. logical :: soil_layers, fraction
  976. logical :: vert_stag = .false.
  977. integer :: vert_unit1, vert_unit2
  978. integer :: vert_sclFctr1, vert_sclFctr2
  979. integer :: level1, level2
  980. integer :: di
  981. real :: tmpreal
  982. call wrf_debug ( DEBUG , 'Entering ext_gr2_read_field'//fileinfo(DataHandle)%DataFile)
  983. CALL get_dims(MemoryOrder, PatchStart, PatchEnd, ndims, x_start, x_end, &
  984. y_start, y_end,z_start,z_end)
  985. xsize = x_end - x_start + 1
  986. ysize = y_end - y_start + 1
  987. zsize = z_end - z_start + 1
  988. !
  989. ! Check to assure that dimensions are valid
  990. !
  991. if ((xsize .lt. 1) .or. (ysize .lt. 1) .or. (zsize .lt. 1)) then
  992. write(msg,*) 'Cannot retrieve field with memory order: ', &
  993. MemoryOrder,Varname
  994. Status = WRF_GRIB2_ERR_READ
  995. call wrf_message(trim(msg))
  996. return
  997. endif
  998. if (ndims .eq. 0) then ! Scalar quantity
  999. call gr2_get_metadata_value(scalar_input(DataHandle),trim(VarName),&
  1000. Value,ierr)
  1001. if (ierr /= 0) then
  1002. Status = WRF_GRIB2_ERR_READ
  1003. CALL wrf_message ( &
  1004. "gr2_get_metadata_value failed for Scalar variable "//&
  1005. trim(VarName))
  1006. return
  1007. endif
  1008. READ(Value,*,IOSTAT=ierr)Data
  1009. if (ierr .ne. 0) then
  1010. CALL wrf_message("Reading data from "//trim(VarName)//" failed")
  1011. Status = WRF_GRIB2_ERR_READ
  1012. return
  1013. endif
  1014. if (FieldType .eq. WRF_INTEGER) then
  1015. Field(1:1) = data
  1016. else if ((FieldType .eq. WRF_REAL) .or. (FieldType .eq. WRF_DOUBLE)) then
  1017. Field(1:1) = TRANSFER(data,Field(1),1)
  1018. else
  1019. write (msg,*)'Reading of type ',FieldType,'from grib data not supported, not reading ',VarName
  1020. call wrf_message(msg)
  1021. endif
  1022. else if (ndims .ge. 1) then ! Vector (1-D) and 2/3 D quantities
  1023. if (ndims .eq. 1) then ! Handle Vector (1-D) parameters
  1024. dim1size = zsize
  1025. dim2size = 1
  1026. dim3size = 1
  1027. else ! Handle 2/3 D parameters
  1028. dim1size = xsize
  1029. dim2size = ysize
  1030. dim3size = zsize
  1031. endif
  1032. CALL get_parminfo(VarName, center, subcenter, MasterTblV, &
  1033. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl, status)
  1034. if (status .ne. 0) then
  1035. write(msg,*) 'Could not find parameter for '// &
  1036. trim(VarName)//' Skipping output of '//trim(VarName)
  1037. call wrf_message(trim(msg))
  1038. Status = WRF_GRIB2_ERR_GRIB2MAP
  1039. return
  1040. endif
  1041. CALL get_vert_stag(VarName,Stagger,vert_stag)
  1042. CALL get_soil_layers(VarName,soil_layers)
  1043. VERTDIM : do dim3 = 1, dim3size
  1044. fields_to_skip = 0
  1045. !
  1046. ! First, set all values to wild, then specify necessary values
  1047. !
  1048. call gr2_g2lib_wildcard(JIDS, JPDT, JGDT)
  1049. JIDS(1) = center
  1050. JIDS(2) = subcenter
  1051. JIDS(3) = MasterTblV
  1052. JIDS(4) = LocalTblV
  1053. JIDS(5) = 1 ! Indicates that time is "Start of Forecast"
  1054. READ (StartDate,'(I4.4,1X,I2.2,1X,I2.2,1X,I2.2,1X,I2.2,1X,I2.2)') &
  1055. (JIDS(idx),idx=6,11)
  1056. JIDS(13) = 1 ! Type of processed data(1 for forecast products)
  1057. JPDT(1) = Category
  1058. JPDT(2) = ParmNum
  1059. JPDT(3) = 2 ! Generating process id
  1060. CALL geth_idts(DateStr,StartDate,tmpreal) ! Forecast time
  1061. JPDT(9) = NINT(tmpreal)
  1062. if (ndims .eq. 1) then
  1063. jpdtn = 1000 ! Product definition tmplate (1000 for cross-sxn)
  1064. else
  1065. call gr2_get_levels(VarName, dim3, dim3size, soil_layers, &
  1066. vert_stag, .false., vert_unit1, vert_unit2, vert_sclFctr1, &
  1067. vert_sclFctr2, level1, level2)
  1068. jpdtn = 0 ! Product definition template (0 for horiz grid)
  1069. JPDT(10) = vert_unit1 ! Type of first surface
  1070. JPDT(11) = vert_sclFctr1 ! Scale factor first surface
  1071. JPDT(12) = level1 ! First surface
  1072. JPDT(13) = vert_unit2 ! Type of second surface
  1073. JPDT(14) = vert_sclFctr2 ! Scale factor second surface
  1074. JPDT(15) = level2 ! Second fixed surface
  1075. endif
  1076. JGDTN = -1 ! Indicates that any Grid Display Template is a match
  1077. UNPACK = .TRUE.! Unpack bitmap and data values
  1078. fields_to_skip = 0
  1079. CALL GETGB2(DataHandle, 0, fields_to_skip, &
  1080. fileinfo(DataHandle)%recnum+1, &
  1081. Disc, JIDS, JPDTN, JPDT, JGDTN, JGDT, UNPACK, &
  1082. fileinfo(DataHandle)%recnum, gfld, status)
  1083. if (status .eq. 99) then
  1084. write(msg,*)'Could not find data for field '//trim(VarName)//&
  1085. ' in file '//trim(fileinfo(DataHandle)%DataFile)
  1086. call wrf_message(trim(msg))
  1087. Status = WRF_GRIB2_ERR_READ
  1088. return
  1089. else if (status .ne. 0) then
  1090. write(msg,*)'Retrieving data field '//trim(VarName)//' failed 2.',status,dim3,DataHandle
  1091. call wrf_message(trim(msg))
  1092. Status = WRF_GRIB2_ERR_READ
  1093. return
  1094. endif
  1095. if(FieldType == WRF_DOUBLE) then
  1096. di = 2
  1097. else
  1098. di = 1
  1099. endif
  1100. !
  1101. ! Here, we do any necessary conversions to the data.
  1102. !
  1103. ! The WRF executable (wrf.exe) expects perturbation potential
  1104. ! temperature. However, real.exe expects full potential T.
  1105. ! So, if the program is WRF, subtract 300 from Potential Temperature
  1106. ! to get perturbation potential temperature.
  1107. !
  1108. if (VarName == 'T') then
  1109. if ( &
  1110. (InputProgramName .eq. 'REAL_EM') .or. &
  1111. (InputProgramName .eq. 'IDEAL') .or. &
  1112. (InputProgramName .eq. 'NDOWN_EM')) then
  1113. gfld%fld = gfld%fld - 300
  1114. endif
  1115. endif
  1116. if (ndims .eq. 1) then
  1117. CALL Transpose1D_grib(MemoryOrder, di, FieldType, Field, &
  1118. MemoryStart(1), MemoryEnd(1), MemoryStart(2), MemoryEnd(2), &
  1119. MemoryStart(3), MemoryEnd(3), &
  1120. gfld%fld, zsize)
  1121. else
  1122. CALL Transpose_grib(MemoryOrder, di, FieldType, Field, &
  1123. MemoryStart(1), MemoryEnd(1), MemoryStart(2), MemoryEnd(2), &
  1124. MemoryStart(3), MemoryEnd(3), &
  1125. gfld%fld, dim3, ysize,xsize)
  1126. endif
  1127. call gf_free(gfld)
  1128. enddo VERTDIM
  1129. endif
  1130. Status = WRF_NO_ERR
  1131. call wrf_debug ( DEBUG , 'Leaving ext_gr2_read_field')
  1132. RETURN
  1133. END SUBROUTINE ext_gr2_read_field
  1134. !*****************************************************************************
  1135. SUBROUTINE ext_gr2_get_next_var ( DataHandle, VarName, Status )
  1136. USE gr2_data_info
  1137. IMPLICIT NONE
  1138. #include "wrf_status_codes.h"
  1139. INTEGER , INTENT(IN) :: DataHandle
  1140. CHARACTER*(*) :: VarName
  1141. INTEGER , INTENT(OUT) :: Status
  1142. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_next_var')
  1143. Status = WRF_WARN_NOOP
  1144. RETURN
  1145. END SUBROUTINE ext_gr2_get_next_var
  1146. !*****************************************************************************
  1147. subroutine ext_gr2_end_of_frame(DataHandle, Status)
  1148. USE gr2_data_info
  1149. implicit none
  1150. #include "wrf_status_codes.h"
  1151. integer ,intent(in) :: DataHandle
  1152. integer ,intent(out) :: Status
  1153. call wrf_debug ( DEBUG , 'Entering ext_gr2_end_of_frame')
  1154. Status = WRF_WARN_NOOP
  1155. return
  1156. end subroutine ext_gr2_end_of_frame
  1157. !*****************************************************************************
  1158. SUBROUTINE ext_gr2_iosync ( DataHandle, Status )
  1159. USE gr2_data_info
  1160. IMPLICIT NONE
  1161. #include "wrf_status_codes.h"
  1162. INTEGER , INTENT(IN) :: DataHandle
  1163. INTEGER , INTENT(OUT) :: Status
  1164. integer :: ierror
  1165. call wrf_debug ( DEBUG , 'Entering ext_gr2_iosync')
  1166. Status = WRF_NO_ERR
  1167. if (DataHandle .GT. 0) then
  1168. CALL flush_file(fileinfo(DataHandle)%FileFd)
  1169. else
  1170. Status = WRF_WARN_TOO_MANY_FILES
  1171. endif
  1172. RETURN
  1173. END SUBROUTINE ext_gr2_iosync
  1174. !*****************************************************************************
  1175. SUBROUTINE ext_gr2_inquire_filename ( DataHandle, FileName , FileStat, &
  1176. Status )
  1177. USE gr2_data_info
  1178. IMPLICIT NONE
  1179. #include "wrf_status_codes.h"
  1180. #include "wrf_io_flags.h"
  1181. INTEGER , INTENT(IN) :: DataHandle
  1182. CHARACTER*(*) :: FileName
  1183. INTEGER , INTENT(OUT) :: FileStat
  1184. INTEGER , INTENT(OUT) :: Status
  1185. CHARACTER *80 SysDepInfo
  1186. call wrf_debug ( DEBUG , 'Entering ext_gr2_inquire_filename')
  1187. FileName = fileinfo(DataHandle)%DataFile
  1188. if ((DataHandle .ge. firstFileHandle) .and. &
  1189. (DataHandle .le. maxFileHandles)) then
  1190. FileStat = fileinfo(DataHandle)%FileStatus
  1191. else
  1192. FileStat = WRF_FILE_NOT_OPENED
  1193. endif
  1194. Status = WRF_NO_ERR
  1195. RETURN
  1196. END SUBROUTINE ext_gr2_inquire_filename
  1197. !*****************************************************************************
  1198. SUBROUTINE ext_gr2_get_var_info ( DataHandle , VarName , NDim , &
  1199. MemoryOrder , Stagger , DomainStart , DomainEnd , WrfType, Status )
  1200. USE gr2_data_info
  1201. IMPLICIT NONE
  1202. #include "wrf_status_codes.h"
  1203. integer ,intent(in) :: DataHandle
  1204. character*(*) ,intent(in) :: VarName
  1205. integer ,intent(out) :: NDim
  1206. character*(*) ,intent(out) :: MemoryOrder
  1207. character*(*) ,intent(out) :: Stagger
  1208. integer ,dimension(*) ,intent(out) :: DomainStart, DomainEnd
  1209. integer ,intent(out) :: WrfType
  1210. integer ,intent(out) :: Status
  1211. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_info')
  1212. MemoryOrder = ""
  1213. Stagger = ""
  1214. DomainStart(1) = 0
  1215. DomainEnd(1) = 0
  1216. WrfType = 0
  1217. NDim = 0
  1218. CALL wrf_message('ext_gr2_get_var_info not supported for grib version2 data')
  1219. Status = WRF_NO_ERR
  1220. RETURN
  1221. END SUBROUTINE ext_gr2_get_var_info
  1222. !*****************************************************************************
  1223. SUBROUTINE ext_gr2_set_time ( DataHandle, DateStr, Status )
  1224. USE gr2_data_info
  1225. IMPLICIT NONE
  1226. #include "wrf_status_codes.h"
  1227. INTEGER , INTENT(IN) :: DataHandle
  1228. CHARACTER*(*) :: DateStr
  1229. INTEGER , INTENT(OUT) :: Status
  1230. integer :: found_time
  1231. integer :: idx
  1232. call wrf_debug ( DEBUG , 'Entering ext_gr2_set_time')
  1233. found_time = 0
  1234. do idx = 1,fileinfo(DataHandle)%NumberTimes
  1235. if (fileinfo(DataHandle)%Times(idx) == DateStr) then
  1236. found_time = 1
  1237. fileinfo(DataHandle)%CurrentTime = idx
  1238. endif
  1239. enddo
  1240. if (found_time == 0) then
  1241. Status = WRF_WARN_TIME_NF
  1242. else
  1243. Status = WRF_NO_ERR
  1244. endif
  1245. RETURN
  1246. END SUBROUTINE ext_gr2_set_time
  1247. !*****************************************************************************
  1248. SUBROUTINE ext_gr2_get_next_time ( DataHandle, DateStr, Status )
  1249. USE gr2_data_info
  1250. IMPLICIT NONE
  1251. #include "wrf_status_codes.h"
  1252. INTEGER , INTENT(IN) :: DataHandle
  1253. CHARACTER*(*) , INTENT(OUT) :: DateStr
  1254. INTEGER , INTENT(OUT) :: Status
  1255. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_next_time')
  1256. if (fileinfo(DataHandle)%CurrentTime == fileinfo(DataHandle)%NumberTimes) then
  1257. Status = WRF_WARN_TIME_EOF
  1258. else
  1259. fileinfo(DataHandle)%CurrentTime = fileinfo(DataHandle)%CurrentTime + 1
  1260. DateStr = fileinfo(DataHandle)%Times(fileinfo(DataHandle)%CurrentTime)
  1261. Status = WRF_NO_ERR
  1262. endif
  1263. call wrf_debug ( DEBUG , 'Leaving ext_gr2_get_next_time, got time '//DateStr)
  1264. RETURN
  1265. END SUBROUTINE ext_gr2_get_next_time
  1266. !*****************************************************************************
  1267. SUBROUTINE ext_gr2_get_previous_time ( DataHandle, DateStr, Status )
  1268. USE gr2_data_info
  1269. IMPLICIT NONE
  1270. #include "wrf_status_codes.h"
  1271. INTEGER , INTENT(IN) :: DataHandle
  1272. CHARACTER*(*) :: DateStr
  1273. INTEGER , INTENT(OUT) :: Status
  1274. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_previous_time')
  1275. if (fileinfo(DataHandle)%CurrentTime <= 0) then
  1276. Status = WRF_WARN_TIME_EOF
  1277. else
  1278. fileinfo(DataHandle)%CurrentTime = fileinfo(DataHandle)%CurrentTime - 1
  1279. DateStr = fileinfo(DataHandle)%Times(fileinfo(DataHandle)%CurrentTime)
  1280. Status = WRF_NO_ERR
  1281. endif
  1282. RETURN
  1283. END SUBROUTINE ext_gr2_get_previous_time
  1284. !******************************************************************************
  1285. !* Start of get_var_ti_* routines
  1286. !******************************************************************************
  1287. SUBROUTINE ext_gr2_get_var_ti_real ( DataHandle,Element, Varname, Data, &
  1288. Count, Outcount, Status )
  1289. USE gr2_data_info
  1290. IMPLICIT NONE
  1291. #include "wrf_status_codes.h"
  1292. INTEGER , INTENT(IN) :: DataHandle
  1293. CHARACTER*(*) :: Element
  1294. CHARACTER*(*) :: VarName
  1295. real , INTENT(OUT) :: Data(*)
  1296. INTEGER , INTENT(IN) :: Count
  1297. INTEGER , INTENT(OUT) :: OutCount
  1298. INTEGER , INTENT(OUT) :: Status
  1299. INTEGER :: idx
  1300. INTEGER :: stat
  1301. CHARACTER(len=100) :: Value
  1302. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_ti_real')
  1303. Status = WRF_NO_ERR
  1304. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1305. trim(VarName)//';'//trim(Element), Value, stat)
  1306. if (stat /= 0) then
  1307. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(Element))
  1308. Status = WRF_WARN_VAR_NF
  1309. RETURN
  1310. endif
  1311. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1312. if (stat .ne. 0) then
  1313. CALL wrf_message("Reading data from"//Value//"failed")
  1314. Status = WRF_WARN_COUNT_TOO_LONG
  1315. RETURN
  1316. endif
  1317. Outcount = idx
  1318. RETURN
  1319. END SUBROUTINE ext_gr2_get_var_ti_real
  1320. !*****************************************************************************
  1321. SUBROUTINE ext_gr2_get_var_ti_real8 ( DataHandle,Element, Varname, Data, &
  1322. Count, Outcount, Status )
  1323. USE gr2_data_info
  1324. IMPLICIT NONE
  1325. #include "wrf_status_codes.h"
  1326. INTEGER , INTENT(IN) :: DataHandle
  1327. CHARACTER*(*) :: Element
  1328. CHARACTER*(*) :: VarName
  1329. real*8 , INTENT(OUT) :: Data(*)
  1330. INTEGER , INTENT(IN) :: Count
  1331. INTEGER , INTENT(OUT) :: OutCount
  1332. INTEGER , INTENT(OUT) :: Status
  1333. INTEGER :: idx
  1334. INTEGER :: stat
  1335. CHARACTER*(100) :: VALUE
  1336. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_ti_real8')
  1337. Status = WRF_NO_ERR
  1338. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1339. trim(VarName)//';'//trim(Element), Value, stat)
  1340. if (stat /= 0) then
  1341. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(Element))
  1342. Status = WRF_WARN_VAR_NF
  1343. RETURN
  1344. endif
  1345. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1346. if (stat .ne. 0) then
  1347. CALL wrf_message("Reading data from"//Value//"failed")
  1348. Status = WRF_WARN_COUNT_TOO_LONG
  1349. RETURN
  1350. endif
  1351. Outcount = idx
  1352. RETURN
  1353. END SUBROUTINE ext_gr2_get_var_ti_real8
  1354. !*****************************************************************************
  1355. SUBROUTINE ext_gr2_get_var_ti_double ( DataHandle,Element, Varname, Data, &
  1356. Count, Outcount, Status )
  1357. USE gr2_data_info
  1358. IMPLICIT NONE
  1359. #include "wrf_status_codes.h"
  1360. INTEGER , INTENT(IN) :: DataHandle
  1361. CHARACTER*(*) , INTENT(IN) :: Element
  1362. CHARACTER*(*) , INTENT(IN) :: VarName
  1363. real*8 , INTENT(OUT) :: Data(*)
  1364. INTEGER , INTENT(IN) :: Count
  1365. INTEGER , INTENT(OUT) :: OutCount
  1366. INTEGER , INTENT(OUT) :: Status
  1367. INTEGER :: idx
  1368. INTEGER :: stat
  1369. CHARACTER*(100) :: VALUE
  1370. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_ti_double')
  1371. Status = WRF_NO_ERR
  1372. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1373. trim(VarName)//';'//trim(Element), Value, stat)
  1374. if (stat /= 0) then
  1375. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(Element))
  1376. Status = WRF_WARN_VAR_NF
  1377. RETURN
  1378. endif
  1379. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1380. if (stat .ne. 0) then
  1381. CALL wrf_message("Reading data from"//Value//"failed")
  1382. Status = WRF_WARN_COUNT_TOO_LONG
  1383. RETURN
  1384. endif
  1385. Outcount = idx
  1386. RETURN
  1387. END SUBROUTINE ext_gr2_get_var_ti_double
  1388. !*****************************************************************************
  1389. SUBROUTINE ext_gr2_get_var_ti_integer ( DataHandle,Element, Varname, Data, &
  1390. Count, Outcount, Status )
  1391. USE gr2_data_info
  1392. IMPLICIT NONE
  1393. #include "wrf_status_codes.h"
  1394. INTEGER , INTENT(IN) :: DataHandle
  1395. CHARACTER*(*) :: Element
  1396. CHARACTER*(*) :: VarName
  1397. integer , INTENT(OUT) :: Data(*)
  1398. INTEGER , INTENT(IN) :: Count
  1399. INTEGER , INTENT(OUT) :: OutCount
  1400. INTEGER , INTENT(OUT) :: Status
  1401. INTEGER :: idx
  1402. INTEGER :: stat
  1403. CHARACTER*(1000) :: VALUE
  1404. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_ti_integer')
  1405. Status = WRF_NO_ERR
  1406. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1407. trim(VarName)//';'//trim(Element), Value, stat)
  1408. if (stat /= 0) then
  1409. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(Element))
  1410. Status = WRF_WARN_VAR_NF
  1411. RETURN
  1412. endif
  1413. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1414. if (stat .ne. 0) then
  1415. CALL wrf_message("Reading data from"//Value//"failed")
  1416. Status = WRF_WARN_COUNT_TOO_LONG
  1417. RETURN
  1418. endif
  1419. Outcount = idx
  1420. RETURN
  1421. END SUBROUTINE ext_gr2_get_var_ti_integer
  1422. !*****************************************************************************
  1423. SUBROUTINE ext_gr2_get_var_ti_logical ( DataHandle,Element, Varname, Data, &
  1424. Count, Outcount, Status )
  1425. USE gr2_data_info
  1426. IMPLICIT NONE
  1427. #include "wrf_status_codes.h"
  1428. INTEGER , INTENT(IN) :: DataHandle
  1429. CHARACTER*(*) :: Element
  1430. CHARACTER*(*) :: VarName
  1431. logical , INTENT(OUT) :: Data(*)
  1432. INTEGER , INTENT(IN) :: Count
  1433. INTEGER , INTENT(OUT) :: OutCount
  1434. INTEGER , INTENT(OUT) :: Status
  1435. INTEGER :: idx
  1436. INTEGER :: stat
  1437. CHARACTER*(100) :: VALUE
  1438. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_ti_logical')
  1439. Status = WRF_NO_ERR
  1440. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1441. trim(VarName)//';'//trim(Element), Value, stat)
  1442. if (stat /= 0) then
  1443. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(Element))
  1444. Status = WRF_WARN_VAR_NF
  1445. RETURN
  1446. endif
  1447. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1448. if (stat .ne. 0) then
  1449. CALL wrf_message("Reading data from"//Value//"failed")
  1450. Status = WRF_WARN_COUNT_TOO_LONG
  1451. RETURN
  1452. endif
  1453. Outcount = idx
  1454. RETURN
  1455. END SUBROUTINE ext_gr2_get_var_ti_logical
  1456. !*****************************************************************************
  1457. SUBROUTINE ext_gr2_get_var_ti_char ( DataHandle,Element, Varname, Data, &
  1458. Status )
  1459. USE gr2_data_info
  1460. IMPLICIT NONE
  1461. #include "wrf_status_codes.h"
  1462. INTEGER , INTENT(IN) :: DataHandle
  1463. CHARACTER*(*) :: Element
  1464. CHARACTER*(*) :: VarName
  1465. CHARACTER*(*) :: Data
  1466. INTEGER , INTENT(OUT) :: Status
  1467. INTEGER :: stat
  1468. Status = WRF_NO_ERR
  1469. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_ti_char')
  1470. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1471. trim(VarName)//';'//trim(Element), Data, stat)
  1472. if (stat /= 0) then
  1473. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(Element))
  1474. Status = WRF_WARN_VAR_NF
  1475. RETURN
  1476. endif
  1477. RETURN
  1478. END SUBROUTINE ext_gr2_get_var_ti_char
  1479. !******************************************************************************
  1480. !* End of get_var_ti_* routines
  1481. !******************************************************************************
  1482. !******************************************************************************
  1483. !* Start of put_var_ti_* routines
  1484. !******************************************************************************
  1485. SUBROUTINE ext_gr2_put_var_ti_real ( DataHandle,Element, Varname, Data, &
  1486. Count, Status )
  1487. USE gr2_data_info
  1488. IMPLICIT NONE
  1489. #include "wrf_status_codes.h"
  1490. INTEGER , INTENT(IN) :: DataHandle
  1491. CHARACTER*(*) :: Element
  1492. CHARACTER*(*) :: VarName
  1493. real , INTENT(IN) :: Data(*)
  1494. INTEGER , INTENT(IN) :: Count
  1495. INTEGER , INTENT(OUT) :: Status
  1496. CHARACTER(len=1000) :: tmpstr(1000)
  1497. INTEGER :: idx
  1498. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_ti_real')
  1499. if (fileinfo(DataHandle)%committed) then
  1500. do idx = 1,Count
  1501. write(tmpstr(idx),'(G17.10)')Data(idx)
  1502. enddo
  1503. CALL gr2_build_string (ti_output(DataHandle), &
  1504. trim(VarName)//';'//trim(Element), tmpstr, Count, Status)
  1505. endif
  1506. RETURN
  1507. END SUBROUTINE ext_gr2_put_var_ti_real
  1508. !*****************************************************************************
  1509. SUBROUTINE ext_gr2_put_var_ti_double ( DataHandle,Element, Varname, Data, &
  1510. Count, Status )
  1511. USE gr2_data_info
  1512. IMPLICIT NONE
  1513. #include "wrf_status_codes.h"
  1514. INTEGER , INTENT(IN) :: DataHandle
  1515. CHARACTER*(*) , INTENT(IN) :: Element
  1516. CHARACTER*(*) , INTENT(IN) :: VarName
  1517. real*8 , INTENT(IN) :: Data(*)
  1518. INTEGER , INTENT(IN) :: Count
  1519. INTEGER , INTENT(OUT) :: Status
  1520. CHARACTER(len=1000) :: tmpstr(1000)
  1521. INTEGER :: idx
  1522. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_ti_double')
  1523. if (fileinfo(DataHandle)%committed) then
  1524. do idx = 1,Count
  1525. write(tmpstr(idx),'(G17.10)')Data(idx)
  1526. enddo
  1527. CALL gr2_build_string (ti_output(DataHandle), &
  1528. trim(VarName)//';'//trim(Element), tmpstr, Count, Status)
  1529. endif
  1530. RETURN
  1531. END SUBROUTINE ext_gr2_put_var_ti_double
  1532. !*****************************************************************************
  1533. SUBROUTINE ext_gr2_put_var_ti_real8 ( DataHandle,Element, Varname, Data, &
  1534. Count, Status )
  1535. USE gr2_data_info
  1536. IMPLICIT NONE
  1537. #include "wrf_status_codes.h"
  1538. INTEGER , INTENT(IN) :: DataHandle
  1539. CHARACTER*(*) :: Element
  1540. CHARACTER*(*) :: VarName
  1541. real*8 , INTENT(IN) :: Data(*)
  1542. INTEGER , INTENT(IN) :: Count
  1543. INTEGER , INTENT(OUT) :: Status
  1544. CHARACTER(len=1000) :: tmpstr(1000)
  1545. INTEGER :: idx
  1546. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_ti_real8')
  1547. if (fileinfo(DataHandle)%committed) then
  1548. do idx = 1,Count
  1549. write(tmpstr(idx),'(G17.10)')Data(idx)
  1550. enddo
  1551. CALL gr2_build_string (ti_output(DataHandle), &
  1552. trim(VarName)//';'//trim(Element), tmpstr, Count, Status)
  1553. endif
  1554. RETURN
  1555. END SUBROUTINE ext_gr2_put_var_ti_real8
  1556. !*****************************************************************************
  1557. SUBROUTINE ext_gr2_put_var_ti_integer ( DataHandle,Element, Varname, Data, &
  1558. Count, Status )
  1559. USE gr2_data_info
  1560. IMPLICIT NONE
  1561. #include "wrf_status_codes.h"
  1562. INTEGER , INTENT(IN) :: DataHandle
  1563. CHARACTER*(*) :: Element
  1564. CHARACTER*(*) :: VarName
  1565. integer , INTENT(IN) :: Data(*)
  1566. INTEGER , INTENT(IN) :: Count
  1567. INTEGER , INTENT(OUT) :: Status
  1568. CHARACTER(len=1000) :: tmpstr(1000)
  1569. INTEGER :: idx
  1570. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_ti_integer')
  1571. if (fileinfo(DataHandle)%committed) then
  1572. do idx = 1,Count
  1573. write(tmpstr(idx),'(G17.10)')Data(idx)
  1574. enddo
  1575. CALL gr2_build_string (ti_output(DataHandle), &
  1576. trim(VarName)//';'//trim(Element), tmpstr, Count, Status)
  1577. endif
  1578. RETURN
  1579. END SUBROUTINE ext_gr2_put_var_ti_integer
  1580. !*****************************************************************************
  1581. SUBROUTINE ext_gr2_put_var_ti_logical ( DataHandle,Element, Varname, Data, &
  1582. Count, Status )
  1583. USE gr2_data_info
  1584. IMPLICIT NONE
  1585. #include "wrf_status_codes.h"
  1586. INTEGER , INTENT(IN) :: DataHandle
  1587. CHARACTER*(*) :: Element
  1588. CHARACTER*(*) :: VarName
  1589. logical , INTENT(IN) :: Data(*)
  1590. INTEGER , INTENT(IN) :: Count
  1591. INTEGER , INTENT(OUT) :: Status
  1592. CHARACTER(len=1000) :: tmpstr(1000)
  1593. INTEGER :: idx
  1594. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_ti_logical')
  1595. if (fileinfo(DataHandle)%committed) then
  1596. do idx = 1,Count
  1597. write(tmpstr(idx),'(G17.10)')Data(idx)
  1598. enddo
  1599. CALL gr2_build_string (ti_output(DataHandle), &
  1600. trim(Varname)//';'//trim(Element), tmpstr, Count, Status)
  1601. endif
  1602. RETURN
  1603. END SUBROUTINE ext_gr2_put_var_ti_logical
  1604. !*****************************************************************************
  1605. SUBROUTINE ext_gr2_put_var_ti_char ( DataHandle,Element, Varname, Data, &
  1606. Status )
  1607. USE gr2_data_info
  1608. IMPLICIT NONE
  1609. #include "wrf_status_codes.h"
  1610. INTEGER , INTENT(IN) :: DataHandle
  1611. CHARACTER(len=*) :: Element
  1612. CHARACTER(len=*) :: VarName
  1613. CHARACTER(len=*) :: Data
  1614. INTEGER , INTENT(OUT) :: Status
  1615. REAL dummy
  1616. INTEGER :: Count
  1617. CHARACTER(len=1000) :: tmpstr(1)
  1618. INTEGER :: idx
  1619. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_ti_char')
  1620. if (fileinfo(DataHandle)%committed) then
  1621. write(tmpstr(1),*)trim(Data)
  1622. CALL gr2_build_string (ti_output(DataHandle), &
  1623. trim(VarName)//';'//trim(Element), tmpstr, 1, Status)
  1624. endif
  1625. RETURN
  1626. END SUBROUTINE ext_gr2_put_var_ti_char
  1627. !******************************************************************************
  1628. !* End of put_var_ti_* routines
  1629. !******************************************************************************
  1630. !******************************************************************************
  1631. !* Start of get_var_td_* routines
  1632. !******************************************************************************
  1633. SUBROUTINE ext_gr2_get_var_td_double ( DataHandle,Element, DateStr, &
  1634. Varname, Data, Count, Outcount, Status )
  1635. USE gr2_data_info
  1636. IMPLICIT NONE
  1637. #include "wrf_status_codes.h"
  1638. INTEGER , INTENT(IN) :: DataHandle
  1639. CHARACTER*(*) , INTENT(IN) :: Element
  1640. CHARACTER*(*) , INTENT(IN) :: DateStr
  1641. CHARACTER*(*) , INTENT(IN) :: VarName
  1642. real*8 , INTENT(OUT) :: Data(*)
  1643. INTEGER , INTENT(IN) :: Count
  1644. INTEGER , INTENT(OUT) :: OutCount
  1645. INTEGER , INTENT(OUT) :: Status
  1646. INTEGER :: idx
  1647. INTEGER :: stat
  1648. CHARACTER*(1000) :: VALUE
  1649. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_td_double')
  1650. Status = WRF_NO_ERR
  1651. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1652. trim(VarName)//';'//trim(DateStr)//';'//trim(Element), Value, stat)
  1653. if (stat /= 0) then
  1654. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(DateStr)//';'//trim(Element))
  1655. Status = WRF_WARN_VAR_NF
  1656. RETURN
  1657. endif
  1658. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1659. if (stat .ne. 0) then
  1660. CALL wrf_message("Reading data from"//Value//"failed")
  1661. Status = WRF_WARN_COUNT_TOO_LONG
  1662. RETURN
  1663. endif
  1664. Outcount = idx
  1665. RETURN
  1666. END SUBROUTINE ext_gr2_get_var_td_double
  1667. !*****************************************************************************
  1668. SUBROUTINE ext_gr2_get_var_td_real ( DataHandle,Element, DateStr,Varname, &
  1669. Data, Count, Outcount, Status )
  1670. USE gr2_data_info
  1671. IMPLICIT NONE
  1672. #include "wrf_status_codes.h"
  1673. INTEGER , INTENT(IN) :: DataHandle
  1674. CHARACTER*(*) :: Element
  1675. CHARACTER*(*) :: DateStr
  1676. CHARACTER*(*) :: VarName
  1677. real , INTENT(OUT) :: Data(*)
  1678. INTEGER , INTENT(IN) :: Count
  1679. INTEGER , INTENT(OUT) :: OutCount
  1680. INTEGER , INTENT(OUT) :: Status
  1681. INTEGER :: idx
  1682. INTEGER :: stat
  1683. CHARACTER*(1000) :: VALUE
  1684. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_td_real')
  1685. Status = WRF_NO_ERR
  1686. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1687. trim(VarName)//';'//trim(DateStr)//';'//trim(Element), Value, stat)
  1688. if (stat /= 0) then
  1689. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(DateStr)//';'//trim(Element))
  1690. Status = WRF_WARN_VAR_NF
  1691. RETURN
  1692. endif
  1693. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1694. if (stat .ne. 0) then
  1695. CALL wrf_message("Reading data from"//Value//"failed")
  1696. Status = WRF_WARN_COUNT_TOO_LONG
  1697. RETURN
  1698. endif
  1699. Outcount = idx
  1700. RETURN
  1701. END SUBROUTINE ext_gr2_get_var_td_real
  1702. !*****************************************************************************
  1703. SUBROUTINE ext_gr2_get_var_td_real8 ( DataHandle,Element, DateStr,Varname, &
  1704. Data, Count, Outcount, Status )
  1705. USE gr2_data_info
  1706. IMPLICIT NONE
  1707. #include "wrf_status_codes.h"
  1708. INTEGER , INTENT(IN) :: DataHandle
  1709. CHARACTER*(*) :: Element
  1710. CHARACTER*(*) :: DateStr
  1711. CHARACTER*(*) :: VarName
  1712. real*8 , INTENT(OUT) :: Data(*)
  1713. INTEGER , INTENT(IN) :: Count
  1714. INTEGER , INTENT(OUT) :: OutCount
  1715. INTEGER , INTENT(OUT) :: Status
  1716. INTEGER :: idx
  1717. INTEGER :: stat
  1718. CHARACTER*(1000) :: VALUE
  1719. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_td_real8')
  1720. Status = WRF_NO_ERR
  1721. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1722. trim(VarName)//';'//trim(DateStr)//';'//trim(Element), Value, stat)
  1723. if (stat /= 0) then
  1724. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(DateStr)//';'//trim(Element))
  1725. Status = WRF_WARN_VAR_NF
  1726. RETURN
  1727. endif
  1728. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1729. if (stat .ne. 0) then
  1730. CALL wrf_message("Reading data from"//Value//"failed")
  1731. Status = WRF_WARN_COUNT_TOO_LONG
  1732. RETURN
  1733. endif
  1734. Outcount = idx
  1735. RETURN
  1736. END SUBROUTINE ext_gr2_get_var_td_real8
  1737. !*****************************************************************************
  1738. SUBROUTINE ext_gr2_get_var_td_integer ( DataHandle,Element, DateStr,Varname, &
  1739. Data, Count, Outcount, Status )
  1740. USE gr2_data_info
  1741. IMPLICIT NONE
  1742. #include "wrf_status_codes.h"
  1743. INTEGER , INTENT(IN) :: DataHandle
  1744. CHARACTER*(*) :: Element
  1745. CHARACTER*(*) :: DateStr
  1746. CHARACTER*(*) :: VarName
  1747. integer , INTENT(OUT) :: Data(*)
  1748. INTEGER , INTENT(IN) :: Count
  1749. INTEGER , INTENT(OUT) :: OutCount
  1750. INTEGER , INTENT(OUT) :: Status
  1751. INTEGER :: idx
  1752. INTEGER :: stat
  1753. CHARACTER*(1000) :: VALUE
  1754. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_td_integer')
  1755. Status = WRF_NO_ERR
  1756. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1757. trim(VarName)//';'//trim(DateStr)//';'//trim(Element), Value, stat)
  1758. if (stat /= 0) then
  1759. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(DateStr)//';'//trim(Element))
  1760. Status = WRF_WARN_VAR_NF
  1761. RETURN
  1762. endif
  1763. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1764. if (stat .ne. 0) then
  1765. CALL wrf_message("Reading data from"//Value//"failed")
  1766. Status = WRF_WARN_COUNT_TOO_LONG
  1767. RETURN
  1768. endif
  1769. Outcount = idx
  1770. RETURN
  1771. END SUBROUTINE ext_gr2_get_var_td_integer
  1772. !*****************************************************************************
  1773. SUBROUTINE ext_gr2_get_var_td_logical ( DataHandle,Element, DateStr,Varname, &
  1774. Data, Count, Outcount, Status )
  1775. USE gr2_data_info
  1776. IMPLICIT NONE
  1777. #include "wrf_status_codes.h"
  1778. INTEGER , INTENT(IN) :: DataHandle
  1779. CHARACTER*(*) :: Element
  1780. CHARACTER*(*) :: DateStr
  1781. CHARACTER*(*) :: VarName
  1782. logical , INTENT(OUT) :: Data(*)
  1783. INTEGER , INTENT(IN) :: Count
  1784. INTEGER , INTENT(OUT) :: OutCount
  1785. INTEGER , INTENT(OUT) :: Status
  1786. INTEGER :: idx
  1787. INTEGER :: stat
  1788. CHARACTER*(1000) :: VALUE
  1789. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_td_logical')
  1790. Status = WRF_NO_ERR
  1791. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1792. trim(VarName)//';'//trim(DateStr)//';'//trim(Element), Value, stat)
  1793. if (stat /= 0) then
  1794. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(DateStr)//';'//trim(Element))
  1795. Status = WRF_WARN_VAR_NF
  1796. RETURN
  1797. endif
  1798. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  1799. if (stat .ne. 0) then
  1800. CALL wrf_message("Reading data from"//Value//"failed")
  1801. Status = WRF_WARN_COUNT_TOO_LONG
  1802. RETURN
  1803. endif
  1804. Outcount = idx
  1805. RETURN
  1806. END SUBROUTINE ext_gr2_get_var_td_logical
  1807. !*****************************************************************************
  1808. SUBROUTINE ext_gr2_get_var_td_char ( DataHandle,Element, DateStr,Varname, &
  1809. Data, Status )
  1810. USE gr2_data_info
  1811. IMPLICIT NONE
  1812. #include "wrf_status_codes.h"
  1813. INTEGER , INTENT(IN) :: DataHandle
  1814. CHARACTER*(*) :: Element
  1815. CHARACTER*(*) :: DateStr
  1816. CHARACTER*(*) :: VarName
  1817. CHARACTER*(*) :: Data
  1818. INTEGER , INTENT(OUT) :: Status
  1819. INTEGER :: stat
  1820. Status = WRF_NO_ERR
  1821. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_var_td_char')
  1822. CALL gr2_get_metadata_value(global_input(DataHandle), &
  1823. trim(VarName)//';'//trim(DateStr)//';'//trim(Element), Data, stat)
  1824. if (stat /= 0) then
  1825. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(VarName)//';'//trim(DateStr)//';'//trim(Element))
  1826. Status = WRF_WARN_VAR_NF
  1827. RETURN
  1828. endif
  1829. RETURN
  1830. END SUBROUTINE ext_gr2_get_var_td_char
  1831. !******************************************************************************
  1832. !* End of get_var_td_* routines
  1833. !******************************************************************************
  1834. !******************************************************************************
  1835. !* Start of put_var_td_* routines
  1836. !******************************************************************************
  1837. SUBROUTINE ext_gr2_put_var_td_double ( DataHandle, Element, DateStr, Varname, &
  1838. Data, Count, Status )
  1839. USE gr2_data_info
  1840. IMPLICIT NONE
  1841. #include "wrf_status_codes.h"
  1842. INTEGER , INTENT(IN) :: DataHandle
  1843. CHARACTER*(*) , INTENT(IN) :: Element
  1844. CHARACTER*(*) , INTENT(IN) :: DateStr
  1845. CHARACTER*(*) , INTENT(IN) :: VarName
  1846. real*8 , INTENT(IN) :: Data(*)
  1847. INTEGER , INTENT(IN) :: Count
  1848. INTEGER , INTENT(OUT) :: Status
  1849. CHARACTER(len=1000) :: tmpstr(1000)
  1850. INTEGER :: idx
  1851. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_td_double')
  1852. if (fileinfo(DataHandle)%committed) then
  1853. do idx = 1,Count
  1854. write(tmpstr(idx),'(G17.10)')Data(idx)
  1855. enddo
  1856. CALL gr2_build_string (td_output(DataHandle), &
  1857. trim(Varname)//';'//trim(DateStr)//';'//trim(Element), &
  1858. tmpstr, Count, Status)
  1859. endif
  1860. RETURN
  1861. END SUBROUTINE ext_gr2_put_var_td_double
  1862. !*****************************************************************************
  1863. SUBROUTINE ext_gr2_put_var_td_integer ( DataHandle,Element, DateStr, &
  1864. Varname, Data, Count, Status )
  1865. USE gr2_data_info
  1866. IMPLICIT NONE
  1867. #include "wrf_status_codes.h"
  1868. INTEGER , INTENT(IN) :: DataHandle
  1869. CHARACTER*(*) :: Element
  1870. CHARACTER*(*) :: DateStr
  1871. CHARACTER*(*) :: VarName
  1872. integer , INTENT(IN) :: Data(*)
  1873. INTEGER , INTENT(IN) :: Count
  1874. INTEGER , INTENT(OUT) :: Status
  1875. CHARACTER(len=1000) :: tmpstr(1000)
  1876. INTEGER :: idx
  1877. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_td_integer')
  1878. if (fileinfo(DataHandle)%committed) then
  1879. do idx = 1,Count
  1880. write(tmpstr(idx),'(G17.10)')Data(idx)
  1881. enddo
  1882. CALL gr2_build_string (td_output(DataHandle), &
  1883. trim(Varname)//';'//trim(DateStr)//';'//trim(Element), &
  1884. tmpstr, Count, Status)
  1885. endif
  1886. RETURN
  1887. END SUBROUTINE ext_gr2_put_var_td_integer
  1888. !*****************************************************************************
  1889. SUBROUTINE ext_gr2_put_var_td_real ( DataHandle,Element, DateStr,Varname, &
  1890. Data, Count, Status )
  1891. USE gr2_data_info
  1892. IMPLICIT NONE
  1893. #include "wrf_status_codes.h"
  1894. INTEGER , INTENT(IN) :: DataHandle
  1895. CHARACTER*(*) :: Element
  1896. CHARACTER*(*) :: DateStr
  1897. CHARACTER*(*) :: VarName
  1898. real , INTENT(IN) :: Data(*)
  1899. INTEGER , INTENT(IN) :: Count
  1900. INTEGER , INTENT(OUT) :: Status
  1901. CHARACTER(len=1000) :: tmpstr(1000)
  1902. INTEGER :: idx
  1903. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_td_real')
  1904. if (fileinfo(DataHandle)%committed) then
  1905. do idx = 1,Count
  1906. write(tmpstr(idx),'(G17.10)')Data(idx)
  1907. enddo
  1908. CALL gr2_build_string (td_output(DataHandle), &
  1909. trim(Varname)//';'//trim(DateStr)//';'//trim(Element), &
  1910. tmpstr, Count, Status)
  1911. endif
  1912. RETURN
  1913. END SUBROUTINE ext_gr2_put_var_td_real
  1914. !*****************************************************************************
  1915. SUBROUTINE ext_gr2_put_var_td_real8 ( DataHandle,Element, DateStr,Varname, &
  1916. Data, Count, Status )
  1917. USE gr2_data_info
  1918. IMPLICIT NONE
  1919. #include "wrf_status_codes.h"
  1920. INTEGER , INTENT(IN) :: DataHandle
  1921. CHARACTER*(*) :: Element
  1922. CHARACTER*(*) :: DateStr
  1923. CHARACTER*(*) :: VarName
  1924. real*8 , INTENT(IN) :: Data(*)
  1925. INTEGER , INTENT(IN) :: Count
  1926. INTEGER , INTENT(OUT) :: Status
  1927. CHARACTER(len=1000) :: tmpstr(1000)
  1928. INTEGER :: idx
  1929. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_td_real8')
  1930. if (fileinfo(DataHandle)%committed) then
  1931. do idx = 1,Count
  1932. write(tmpstr(idx),'(G17.10)')Data(idx)
  1933. enddo
  1934. CALL gr2_build_string (td_output(DataHandle), &
  1935. trim(Varname)//';'//trim(DateStr)//';'//trim(Element), &
  1936. tmpstr, Count, Status)
  1937. endif
  1938. RETURN
  1939. END SUBROUTINE ext_gr2_put_var_td_real8
  1940. !*****************************************************************************
  1941. SUBROUTINE ext_gr2_put_var_td_logical ( DataHandle,Element, DateStr, &
  1942. Varname, Data, Count, Status )
  1943. USE gr2_data_info
  1944. IMPLICIT NONE
  1945. #include "wrf_status_codes.h"
  1946. INTEGER , INTENT(IN) :: DataHandle
  1947. CHARACTER*(*) :: Element
  1948. CHARACTER*(*) :: DateStr
  1949. CHARACTER*(*) :: VarName
  1950. logical , INTENT(IN) :: Data(*)
  1951. INTEGER , INTENT(IN) :: Count
  1952. INTEGER , INTENT(OUT) :: Status
  1953. CHARACTER(len=1000) :: tmpstr(1000)
  1954. INTEGER :: idx
  1955. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_td_logical')
  1956. if (fileinfo(DataHandle)%committed) then
  1957. do idx = 1,Count
  1958. write(tmpstr(idx),'(G17.10)')Data(idx)
  1959. enddo
  1960. CALL gr2_build_string (td_output(DataHandle), &
  1961. trim(Varname)//';'//trim(DateStr)//';'//trim(Element), &
  1962. tmpstr, Count, Status)
  1963. endif
  1964. RETURN
  1965. END SUBROUTINE ext_gr2_put_var_td_logical
  1966. !*****************************************************************************
  1967. SUBROUTINE ext_gr2_put_var_td_char ( DataHandle,Element, DateStr,Varname, &
  1968. Data, Status )
  1969. USE gr2_data_info
  1970. IMPLICIT NONE
  1971. #include "wrf_status_codes.h"
  1972. INTEGER , INTENT(IN) :: DataHandle
  1973. CHARACTER*(*) :: Element
  1974. CHARACTER*(*) :: DateStr
  1975. CHARACTER*(*) :: VarName
  1976. CHARACTER*(*) :: Data
  1977. INTEGER , INTENT(OUT) :: Status
  1978. CHARACTER(len=1000) :: tmpstr(1)
  1979. INTEGER :: idx
  1980. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_var_td_char')
  1981. if (fileinfo(DataHandle)%committed) then
  1982. write(tmpstr(idx),*)Data
  1983. CALL gr2_build_string (td_output(DataHandle), &
  1984. trim(Varname)//';'//trim(DateStr)//';'//trim(Element), &
  1985. tmpstr, 1, Status)
  1986. endif
  1987. RETURN
  1988. END SUBROUTINE ext_gr2_put_var_td_char
  1989. !******************************************************************************
  1990. !* End of put_var_td_* routines
  1991. !******************************************************************************
  1992. !******************************************************************************
  1993. !* Start of get_dom_ti_* routines
  1994. !******************************************************************************
  1995. SUBROUTINE ext_gr2_get_dom_ti_real ( DataHandle,Element, Data, Count, &
  1996. Outcount, Status )
  1997. USE gr2_data_info
  1998. IMPLICIT NONE
  1999. #include "wrf_status_codes.h"
  2000. INTEGER , INTENT(IN) :: DataHandle
  2001. CHARACTER*(*) :: Element
  2002. real , INTENT(OUT) :: Data(*)
  2003. INTEGER , INTENT(IN) :: Count
  2004. INTEGER , INTENT(OUT) :: Outcount
  2005. INTEGER , INTENT(OUT) :: Status
  2006. INTEGER :: idx
  2007. INTEGER :: stat
  2008. CHARACTER*(1000) :: VALUE
  2009. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_ti_real')
  2010. Status = WRF_NO_ERR
  2011. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2012. trim(Element), Value, stat)
  2013. if (stat /= 0) then
  2014. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(Element))
  2015. Status = WRF_WARN_VAR_NF
  2016. RETURN
  2017. endif
  2018. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2019. if (stat .ne. 0) then
  2020. CALL wrf_message("Reading data from"//Value//"failed")
  2021. Status = WRF_WARN_COUNT_TOO_LONG
  2022. RETURN
  2023. endif
  2024. Outcount = idx
  2025. RETURN
  2026. END SUBROUTINE ext_gr2_get_dom_ti_real
  2027. !*****************************************************************************
  2028. SUBROUTINE ext_gr2_get_dom_ti_real8 ( DataHandle,Element, Data, Count, &
  2029. Outcount, Status )
  2030. USE gr2_data_info
  2031. IMPLICIT NONE
  2032. #include "wrf_status_codes.h"
  2033. INTEGER , INTENT(IN) :: DataHandle
  2034. CHARACTER*(*) :: Element
  2035. real*8 , INTENT(OUT) :: Data(*)
  2036. INTEGER , INTENT(IN) :: Count
  2037. INTEGER , INTENT(OUT) :: OutCount
  2038. INTEGER , INTENT(OUT) :: Status
  2039. INTEGER :: idx
  2040. INTEGER :: stat
  2041. CHARACTER*(1000) :: VALUE
  2042. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_ti_real8')
  2043. Status = WRF_NO_ERR
  2044. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2045. trim(Element), Value, stat)
  2046. if (stat /= 0) then
  2047. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(Element))
  2048. Status = WRF_WARN_VAR_NF
  2049. RETURN
  2050. endif
  2051. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2052. if (stat .ne. 0) then
  2053. CALL wrf_message("Reading data from"//Value//"failed")
  2054. Status = WRF_WARN_COUNT_TOO_LONG
  2055. RETURN
  2056. endif
  2057. Outcount = idx
  2058. RETURN
  2059. END SUBROUTINE ext_gr2_get_dom_ti_real8
  2060. !*****************************************************************************
  2061. SUBROUTINE ext_gr2_get_dom_ti_integer ( DataHandle,Element, Data, Count, &
  2062. Outcount, Status )
  2063. USE gr2_data_info
  2064. IMPLICIT NONE
  2065. #include "wrf_status_codes.h"
  2066. INTEGER , INTENT(IN) :: DataHandle
  2067. CHARACTER*(*) :: Element
  2068. integer , INTENT(OUT) :: Data(*)
  2069. INTEGER , INTENT(IN) :: Count
  2070. INTEGER , INTENT(OUT) :: OutCount
  2071. INTEGER , INTENT(OUT) :: Status
  2072. INTEGER :: idx
  2073. INTEGER :: stat
  2074. CHARACTER*(1000) :: VALUE
  2075. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_ti_integer Element: '//Element)
  2076. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2077. trim(Element), Value, stat)
  2078. if (stat /= 0) then
  2079. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(Element))
  2080. Status = WRF_WARN_VAR_NF
  2081. RETURN
  2082. endif
  2083. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2084. if (stat .ne. 0) then
  2085. CALL wrf_message("Reading data from"//Value//"failed")
  2086. Status = WRF_WARN_COUNT_TOO_LONG
  2087. RETURN
  2088. endif
  2089. Outcount = Count
  2090. RETURN
  2091. END SUBROUTINE ext_gr2_get_dom_ti_integer
  2092. !*****************************************************************************
  2093. SUBROUTINE ext_gr2_get_dom_ti_logical ( DataHandle,Element, Data, Count, &
  2094. Outcount, Status )
  2095. USE gr2_data_info
  2096. IMPLICIT NONE
  2097. #include "wrf_status_codes.h"
  2098. INTEGER , INTENT(IN) :: DataHandle
  2099. CHARACTER*(*) :: Element
  2100. logical , INTENT(OUT) :: Data(*)
  2101. INTEGER , INTENT(IN) :: Count
  2102. INTEGER , INTENT(OUT) :: OutCount
  2103. INTEGER , INTENT(OUT) :: Status
  2104. INTEGER :: idx
  2105. INTEGER :: stat
  2106. CHARACTER*(1000) :: VALUE
  2107. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_ti_logical')
  2108. Status = WRF_NO_ERR
  2109. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2110. trim(Element), Value, stat)
  2111. if (stat /= 0) then
  2112. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(Element))
  2113. Status = WRF_WARN_VAR_NF
  2114. RETURN
  2115. endif
  2116. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2117. if (stat .ne. 0) then
  2118. CALL wrf_message("Reading data from"//Value//"failed")
  2119. Status = WRF_WARN_COUNT_TOO_LONG
  2120. RETURN
  2121. endif
  2122. Outcount = idx
  2123. RETURN
  2124. END SUBROUTINE ext_gr2_get_dom_ti_logical
  2125. !*****************************************************************************
  2126. SUBROUTINE ext_gr2_get_dom_ti_char ( DataHandle,Element, Data, Status )
  2127. USE gr2_data_info
  2128. IMPLICIT NONE
  2129. #include "wrf_status_codes.h"
  2130. INTEGER , INTENT(IN) :: DataHandle
  2131. CHARACTER*(*) :: Element
  2132. CHARACTER*(*) :: Data
  2133. INTEGER , INTENT(OUT) :: Status
  2134. INTEGER :: stat
  2135. INTEGER :: endchar
  2136. Status = WRF_NO_ERR
  2137. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_ti_char')
  2138. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2139. trim(Element), Data, stat)
  2140. if (stat /= 0) then
  2141. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(Element))
  2142. Status = WRF_WARN_VAR_NF
  2143. RETURN
  2144. endif
  2145. RETURN
  2146. END SUBROUTINE ext_gr2_get_dom_ti_char
  2147. !*****************************************************************************
  2148. SUBROUTINE ext_gr2_get_dom_ti_double ( DataHandle,Element, Data, Count, &
  2149. Outcount, Status )
  2150. USE gr2_data_info
  2151. IMPLICIT NONE
  2152. #include "wrf_status_codes.h"
  2153. INTEGER , INTENT(IN) :: DataHandle
  2154. CHARACTER*(*) , INTENT(IN) :: Element
  2155. real*8 , INTENT(OUT) :: Data(*)
  2156. INTEGER , INTENT(IN) :: Count
  2157. INTEGER , INTENT(OUT) :: OutCount
  2158. INTEGER , INTENT(OUT) :: Status
  2159. INTEGER :: idx
  2160. INTEGER :: stat
  2161. CHARACTER*(1000) :: VALUE
  2162. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_ti_double')
  2163. Status = WRF_NO_ERR
  2164. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2165. trim(Element), Value, stat)
  2166. if (stat /= 0) then
  2167. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(Element))
  2168. Status = WRF_WARN_VAR_NF
  2169. RETURN
  2170. endif
  2171. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2172. if (stat .ne. 0) then
  2173. CALL wrf_message("Reading data from"//Value//"failed")
  2174. Status = WRF_WARN_COUNT_TOO_LONG
  2175. RETURN
  2176. endif
  2177. Outcount = idx
  2178. RETURN
  2179. END SUBROUTINE ext_gr2_get_dom_ti_double
  2180. !******************************************************************************
  2181. !* End of get_dom_ti_* routines
  2182. !******************************************************************************
  2183. !******************************************************************************
  2184. !* Start of put_dom_ti_* routines
  2185. !******************************************************************************
  2186. SUBROUTINE ext_gr2_put_dom_ti_real ( DataHandle,Element, Data, Count, &
  2187. Status )
  2188. USE gr2_data_info
  2189. IMPLICIT NONE
  2190. #include "wrf_status_codes.h"
  2191. INTEGER , INTENT(IN) :: DataHandle
  2192. CHARACTER*(*) :: Element
  2193. real , INTENT(IN) :: Data(*)
  2194. INTEGER , INTENT(IN) :: Count
  2195. INTEGER , INTENT(OUT) :: Status
  2196. REAL dummy
  2197. CHARACTER(len=1000) :: tmpstr(1000)
  2198. character(len=2) :: lf
  2199. integer :: idx
  2200. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_ti_real')
  2201. if (Element .eq. 'DX') then
  2202. dx = Data(1)/1000.
  2203. endif
  2204. if (Element .eq. 'DY') then
  2205. dy = Data(1)/1000.
  2206. endif
  2207. if (Element .eq. 'CEN_LAT') then
  2208. center_lat = Data(1)
  2209. endif
  2210. if (Element .eq. 'CEN_LON') then
  2211. center_lon = Data(1)
  2212. endif
  2213. if (Element .eq. 'TRUELAT1') then
  2214. truelat1 = Data(1)
  2215. endif
  2216. if (Element .eq. 'TRUELAT2') then
  2217. truelat2 = Data(1)
  2218. endif
  2219. if (Element == 'STAND_LON') then
  2220. proj_central_lon = Data(1)
  2221. endif
  2222. if (Element == 'DT') then
  2223. timestep = Data(1)
  2224. endif
  2225. if (fileinfo(DataHandle)%committed) then
  2226. do idx = 1,Count
  2227. write(tmpstr(idx),'(G17.10)')Data(idx)
  2228. enddo
  2229. CALL gr2_build_string (ti_output(DataHandle), Element, &
  2230. tmpstr, Count, Status)
  2231. endif
  2232. RETURN
  2233. END SUBROUTINE ext_gr2_put_dom_ti_real
  2234. !*****************************************************************************
  2235. SUBROUTINE ext_gr2_put_dom_ti_real8 ( DataHandle,Element, Data, Count, &
  2236. Status )
  2237. USE gr2_data_info
  2238. IMPLICIT NONE
  2239. #include "wrf_status_codes.h"
  2240. INTEGER , INTENT(IN) :: DataHandle
  2241. CHARACTER*(*) :: Element
  2242. real*8 , INTENT(IN) :: Data(*)
  2243. INTEGER , INTENT(IN) :: Count
  2244. INTEGER , INTENT(OUT) :: Status
  2245. CHARACTER(len=1000) :: tmpstr(1000)
  2246. INTEGER :: idx
  2247. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_ti_real8')
  2248. if (fileinfo(DataHandle)%committed) then
  2249. do idx = 1,Count
  2250. write(tmpstr(idx),'(G17.10)')Data(idx)
  2251. enddo
  2252. CALL gr2_build_string (ti_output(DataHandle), Element, &
  2253. tmpstr, Count, Status)
  2254. endif
  2255. RETURN
  2256. END SUBROUTINE ext_gr2_put_dom_ti_real8
  2257. !*****************************************************************************
  2258. SUBROUTINE ext_gr2_put_dom_ti_integer ( DataHandle,Element, Data, Count, &
  2259. Status )
  2260. USE gr2_data_info
  2261. IMPLICIT NONE
  2262. #include "wrf_status_codes.h"
  2263. INTEGER , INTENT(IN) :: DataHandle
  2264. CHARACTER*(*) :: Element
  2265. INTEGER , INTENT(IN) :: Data(*)
  2266. INTEGER , INTENT(IN) :: Count
  2267. INTEGER , INTENT(OUT) :: Status
  2268. REAL dummy
  2269. CHARACTER(len=1000) :: tmpstr(1000)
  2270. INTEGER :: idx
  2271. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_ti_integer')
  2272. if (Element == 'WEST-EAST_GRID_DIMENSION') then
  2273. full_xsize = Data(1)
  2274. else if (Element == 'SOUTH-NORTH_GRID_DIMENSION') then
  2275. full_ysize = Data(1)
  2276. else if (Element == 'MAP_PROJ') then
  2277. wrf_projection = Data(1)
  2278. else if (Element == 'BACKGROUND_PROC_ID') then
  2279. background_proc_id = Data(1)
  2280. else if (Element == 'FORECAST_PROC_ID') then
  2281. forecast_proc_id = Data(1)
  2282. else if (Element == 'PRODUCTION_STATUS') then
  2283. production_status = Data(1)
  2284. else if (Element == 'COMPRESSION') then
  2285. compression = Data(1)
  2286. endif
  2287. if (fileinfo(DataHandle)%committed) then
  2288. do idx = 1,Count
  2289. write(tmpstr(idx),'(G17.10)')Data(idx)
  2290. enddo
  2291. CALL gr2_build_string (ti_output(DataHandle), Element, &
  2292. tmpstr, Count, Status)
  2293. endif
  2294. call wrf_debug ( DEBUG , 'Leaving ext_gr2_put_dom_ti_integer')
  2295. RETURN
  2296. END SUBROUTINE ext_gr2_put_dom_ti_integer
  2297. !*****************************************************************************
  2298. SUBROUTINE ext_gr2_put_dom_ti_logical ( DataHandle,Element, Data, Count, &
  2299. Status )
  2300. USE gr2_data_info
  2301. IMPLICIT NONE
  2302. #include "wrf_status_codes.h"
  2303. INTEGER , INTENT(IN) :: DataHandle
  2304. CHARACTER*(*) :: Element
  2305. logical , INTENT(IN) :: Data(*)
  2306. INTEGER , INTENT(IN) :: Count
  2307. INTEGER , INTENT(OUT) :: Status
  2308. CHARACTER(len=1000) :: tmpstr(1000)
  2309. INTEGER :: idx
  2310. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_ti_logical')
  2311. if (fileinfo(DataHandle)%committed) then
  2312. do idx = 1,Count
  2313. write(tmpstr(idx),'(G17.10)')Data(idx)
  2314. enddo
  2315. CALL gr2_build_string (ti_output(DataHandle), Element, &
  2316. tmpstr, Count, Status)
  2317. endif
  2318. RETURN
  2319. END SUBROUTINE ext_gr2_put_dom_ti_logical
  2320. !*****************************************************************************
  2321. SUBROUTINE ext_gr2_put_dom_ti_char ( DataHandle,Element, Data, &
  2322. Status )
  2323. USE gr2_data_info
  2324. IMPLICIT NONE
  2325. #include "wrf_status_codes.h"
  2326. INTEGER , INTENT(IN) :: DataHandle
  2327. CHARACTER*(*) :: Element
  2328. CHARACTER*(*), INTENT(IN) :: Data
  2329. INTEGER , INTENT(OUT) :: Status
  2330. REAL dummy
  2331. CHARACTER(len=1000) :: tmpstr
  2332. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_ti_char')
  2333. if (Element .eq. 'START_DATE') then
  2334. !
  2335. ! This is just a hack to fix a problem when outputting restart. WRF
  2336. ! outputs both the initialization time and the time of the restart
  2337. ! as the StartDate. So, we ll just take the earliest.
  2338. !
  2339. if ((StartDate .eq. '') .or. (Data .le. StartDate)) then
  2340. StartDate = Data
  2341. endif
  2342. endif
  2343. if (fileinfo(DataHandle)%committed) then
  2344. write(tmpstr,*)trim(Data)
  2345. CALL gr2_build_string (ti_output(DataHandle), Element, &
  2346. tmpstr, 1, Status)
  2347. endif
  2348. RETURN
  2349. END SUBROUTINE ext_gr2_put_dom_ti_char
  2350. !*****************************************************************************
  2351. SUBROUTINE ext_gr2_put_dom_ti_double ( DataHandle,Element, Data, Count, &
  2352. Status )
  2353. USE gr2_data_info
  2354. IMPLICIT NONE
  2355. #include "wrf_status_codes.h"
  2356. INTEGER , INTENT(IN) :: DataHandle
  2357. CHARACTER*(*) , INTENT(IN) :: Element
  2358. real*8 , INTENT(IN) :: Data(*)
  2359. INTEGER , INTENT(IN) :: Count
  2360. INTEGER , INTENT(OUT) :: Status
  2361. CHARACTER(len=1000) :: tmpstr(1000)
  2362. INTEGER :: idx
  2363. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_ti_double')
  2364. if (fileinfo(DataHandle)%committed) then
  2365. do idx = 1,Count
  2366. write(tmpstr(idx),'(G17.10)')Data(idx)
  2367. enddo
  2368. CALL gr2_build_string (ti_output(DataHandle), Element, &
  2369. tmpstr, Count, Status)
  2370. endif
  2371. RETURN
  2372. END SUBROUTINE ext_gr2_put_dom_ti_double
  2373. !******************************************************************************
  2374. !* End of put_dom_ti_* routines
  2375. !******************************************************************************
  2376. !******************************************************************************
  2377. !* Start of get_dom_td_* routines
  2378. !******************************************************************************
  2379. SUBROUTINE ext_gr2_get_dom_td_real ( DataHandle,Element, DateStr, Data, &
  2380. Count, Outcount, Status )
  2381. USE gr2_data_info
  2382. IMPLICIT NONE
  2383. #include "wrf_status_codes.h"
  2384. INTEGER , INTENT(IN) :: DataHandle
  2385. CHARACTER*(*) :: Element
  2386. CHARACTER*(*) :: DateStr
  2387. real , INTENT(OUT) :: Data(*)
  2388. INTEGER , INTENT(IN) :: Count
  2389. INTEGER , INTENT(OUT) :: OutCount
  2390. INTEGER , INTENT(OUT) :: Status
  2391. INTEGER :: idx
  2392. INTEGER :: stat
  2393. CHARACTER*(1000) :: VALUE
  2394. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_td_real')
  2395. Status = WRF_NO_ERR
  2396. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2397. trim(DateStr)//';'//trim(Element), Value, stat)
  2398. if (stat /= 0) then
  2399. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(DateStr)//';'//trim(Element))
  2400. Status = WRF_WARN_VAR_NF
  2401. RETURN
  2402. endif
  2403. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2404. if (stat .ne. 0) then
  2405. CALL wrf_message("Reading data from"//Value//"failed")
  2406. Status = WRF_WARN_COUNT_TOO_LONG
  2407. RETURN
  2408. endif
  2409. Outcount = idx
  2410. RETURN
  2411. END SUBROUTINE ext_gr2_get_dom_td_real
  2412. !*****************************************************************************
  2413. SUBROUTINE ext_gr2_get_dom_td_real8 ( DataHandle,Element, DateStr, Data, &
  2414. Count, Outcount, Status )
  2415. USE gr2_data_info
  2416. IMPLICIT NONE
  2417. #include "wrf_status_codes.h"
  2418. INTEGER , INTENT(IN) :: DataHandle
  2419. CHARACTER*(*) :: Element
  2420. CHARACTER*(*) :: DateStr
  2421. real*8 , INTENT(OUT) :: Data(*)
  2422. INTEGER , INTENT(IN) :: Count
  2423. INTEGER , INTENT(OUT) :: OutCount
  2424. INTEGER , INTENT(OUT) :: Status
  2425. INTEGER :: idx
  2426. INTEGER :: stat
  2427. CHARACTER*(1000) :: VALUE
  2428. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_td_real8')
  2429. Status = WRF_NO_ERR
  2430. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2431. trim(DateStr)//';'//trim(Element), Value, stat)
  2432. if (stat /= 0) then
  2433. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(DateStr)//';'//trim(Element))
  2434. Status = WRF_WARN_VAR_NF
  2435. RETURN
  2436. endif
  2437. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2438. if (stat .ne. 0) then
  2439. CALL wrf_message("Reading data from"//Value//"failed")
  2440. Status = WRF_WARN_COUNT_TOO_LONG
  2441. RETURN
  2442. endif
  2443. Outcount = idx
  2444. RETURN
  2445. END SUBROUTINE ext_gr2_get_dom_td_real8
  2446. !*****************************************************************************
  2447. SUBROUTINE ext_gr2_get_dom_td_integer ( DataHandle,Element, DateStr, Data, &
  2448. Count, Outcount, Status )
  2449. USE gr2_data_info
  2450. IMPLICIT NONE
  2451. #include "wrf_status_codes.h"
  2452. INTEGER , INTENT(IN) :: DataHandle
  2453. CHARACTER*(*) :: Element
  2454. CHARACTER*(*) :: DateStr
  2455. integer , INTENT(OUT) :: Data(*)
  2456. INTEGER , INTENT(IN) :: Count
  2457. INTEGER , INTENT(OUT) :: OutCount
  2458. INTEGER , INTENT(OUT) :: Status
  2459. INTEGER :: idx
  2460. INTEGER :: stat
  2461. CHARACTER*(1000) :: VALUE
  2462. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_td_integer')
  2463. Status = WRF_NO_ERR
  2464. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2465. trim(DateStr)//';'//trim(Element), Value, stat)
  2466. if (stat /= 0) then
  2467. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(DateStr)//';'//trim(Element))
  2468. Status = WRF_WARN_VAR_NF
  2469. RETURN
  2470. endif
  2471. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2472. if (stat .ne. 0) then
  2473. CALL wrf_message("Reading data from"//Value//"failed")
  2474. Status = WRF_WARN_COUNT_TOO_LONG
  2475. RETURN
  2476. endif
  2477. Outcount = idx
  2478. RETURN
  2479. END SUBROUTINE ext_gr2_get_dom_td_integer
  2480. !*****************************************************************************
  2481. SUBROUTINE ext_gr2_get_dom_td_logical ( DataHandle,Element, DateStr, Data, &
  2482. Count, Outcount, Status )
  2483. USE gr2_data_info
  2484. IMPLICIT NONE
  2485. #include "wrf_status_codes.h"
  2486. INTEGER , INTENT(IN) :: DataHandle
  2487. CHARACTER*(*) :: Element
  2488. CHARACTER*(*) :: DateStr
  2489. logical , INTENT(OUT) :: Data(*)
  2490. INTEGER , INTENT(IN) :: Count
  2491. INTEGER , INTENT(OUT) :: OutCount
  2492. INTEGER , INTENT(OUT) :: Status
  2493. INTEGER :: idx
  2494. INTEGER :: stat
  2495. CHARACTER*(1000) :: VALUE
  2496. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_td_logical')
  2497. Status = WRF_NO_ERR
  2498. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2499. trim(DateStr)//';'//trim(Element), Value, stat)
  2500. if (stat /= 0) then
  2501. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(DateStr)//';'//trim(Element))
  2502. Status = WRF_WARN_VAR_NF
  2503. RETURN
  2504. endif
  2505. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2506. if (stat .ne. 0) then
  2507. CALL wrf_message("Reading data from"//Value//"failed")
  2508. Status = WRF_WARN_COUNT_TOO_LONG
  2509. RETURN
  2510. endif
  2511. Outcount = idx
  2512. RETURN
  2513. END SUBROUTINE ext_gr2_get_dom_td_logical
  2514. !*****************************************************************************
  2515. SUBROUTINE ext_gr2_get_dom_td_char ( DataHandle,Element, DateStr, Data, &
  2516. Status )
  2517. USE gr2_data_info
  2518. IMPLICIT NONE
  2519. #include "wrf_status_codes.h"
  2520. INTEGER , INTENT(IN) :: DataHandle
  2521. CHARACTER*(*) :: Element
  2522. CHARACTER*(*) :: DateStr
  2523. CHARACTER*(*) :: Data
  2524. INTEGER , INTENT(OUT) :: Status
  2525. INTEGER :: stat
  2526. Status = WRF_NO_ERR
  2527. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_td_char')
  2528. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2529. trim(DateStr)//';'//trim(Element), Data, stat)
  2530. if (stat /= 0) then
  2531. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(DateStr)//';'//trim(Element))
  2532. Status = WRF_WARN_VAR_NF
  2533. RETURN
  2534. endif
  2535. RETURN
  2536. END SUBROUTINE ext_gr2_get_dom_td_char
  2537. !*****************************************************************************
  2538. SUBROUTINE ext_gr2_get_dom_td_double ( DataHandle,Element, DateStr, Data, &
  2539. Count, Outcount, Status )
  2540. USE gr2_data_info
  2541. IMPLICIT NONE
  2542. #include "wrf_status_codes.h"
  2543. INTEGER , INTENT(IN) :: DataHandle
  2544. CHARACTER*(*) , INTENT(IN) :: Element
  2545. CHARACTER*(*) , INTENT(IN) :: DateStr
  2546. real*8 , INTENT(OUT) :: Data(*)
  2547. INTEGER , INTENT(IN) :: Count
  2548. INTEGER , INTENT(OUT) :: OutCount
  2549. INTEGER , INTENT(OUT) :: Status
  2550. INTEGER :: idx
  2551. INTEGER :: stat
  2552. CHARACTER*(1000) :: VALUE
  2553. call wrf_debug ( DEBUG , 'Entering ext_gr2_get_dom_td_double')
  2554. Status = WRF_NO_ERR
  2555. CALL gr2_get_metadata_value(global_input(DataHandle), &
  2556. trim(DateStr)//';'//trim(Element), Value, stat)
  2557. if (stat /= 0) then
  2558. CALL wrf_debug ( DEBUG , "gr2_get_metadata_value failed for "//trim(DateStr)//';'//trim(Element))
  2559. Status = WRF_WARN_VAR_NF
  2560. RETURN
  2561. endif
  2562. READ(Value,*,IOSTAT=stat)(Data(idx),idx=1,Count)
  2563. if (stat .ne. 0) then
  2564. CALL wrf_message("Reading data from"//Value//"failed")
  2565. Status = WRF_WARN_COUNT_TOO_LONG
  2566. RETURN
  2567. endif
  2568. Outcount = idx
  2569. RETURN
  2570. END SUBROUTINE ext_gr2_get_dom_td_double
  2571. !******************************************************************************
  2572. !* End of get_dom_td_* routines
  2573. !******************************************************************************
  2574. !******************************************************************************
  2575. !* Start of put_dom_td_* routines
  2576. !******************************************************************************
  2577. SUBROUTINE ext_gr2_put_dom_td_real8 ( DataHandle,Element, DateStr, Data, &
  2578. Count, Status )
  2579. USE gr2_data_info
  2580. IMPLICIT NONE
  2581. #include "wrf_status_codes.h"
  2582. INTEGER , INTENT(IN) :: DataHandle
  2583. CHARACTER*(*) :: Element
  2584. CHARACTER*(*) :: DateStr
  2585. real*8 , INTENT(IN) :: Data(*)
  2586. INTEGER , INTENT(IN) :: Count
  2587. INTEGER , INTENT(OUT) :: Status
  2588. CHARACTER(len=1000) :: tmpstr(1000)
  2589. INTEGER :: idx
  2590. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_td_real8')
  2591. if (fileinfo(DataHandle)%committed) then
  2592. do idx = 1,Count
  2593. write(tmpstr(idx),'(G17.10)')Data(idx)
  2594. enddo
  2595. CALL gr2_build_string (td_output(DataHandle), &
  2596. trim(DateStr)//';'//trim(Element), tmpstr, &
  2597. Count, Status)
  2598. endif
  2599. RETURN
  2600. END SUBROUTINE ext_gr2_put_dom_td_real8
  2601. !*****************************************************************************
  2602. SUBROUTINE ext_gr2_put_dom_td_integer ( DataHandle,Element, DateStr, Data, &
  2603. Count, Status )
  2604. USE gr2_data_info
  2605. IMPLICIT NONE
  2606. #include "wrf_status_codes.h"
  2607. INTEGER , INTENT(IN) :: DataHandle
  2608. CHARACTER*(*) :: Element
  2609. CHARACTER*(*) :: DateStr
  2610. integer , INTENT(IN) :: Data(*)
  2611. INTEGER , INTENT(IN) :: Count
  2612. INTEGER , INTENT(OUT) :: Status
  2613. CHARACTER(len=1000) :: tmpstr(1000)
  2614. INTEGER :: idx
  2615. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_td_integer')
  2616. if (fileinfo(DataHandle)%committed) then
  2617. do idx = 1,Count
  2618. write(tmpstr(idx),'(G17.10)')Data(idx)
  2619. enddo
  2620. CALL gr2_build_string (td_output(DataHandle), &
  2621. trim(DateStr)//';'//trim(Element), tmpstr, &
  2622. Count, Status)
  2623. endif
  2624. RETURN
  2625. END SUBROUTINE ext_gr2_put_dom_td_integer
  2626. !*****************************************************************************
  2627. SUBROUTINE ext_gr2_put_dom_td_logical ( DataHandle,Element, DateStr, Data, &
  2628. Count, Status )
  2629. USE gr2_data_info
  2630. IMPLICIT NONE
  2631. #include "wrf_status_codes.h"
  2632. INTEGER , INTENT(IN) :: DataHandle
  2633. CHARACTER*(*) :: Element
  2634. CHARACTER*(*) :: DateStr
  2635. logical , INTENT(IN) :: Data(*)
  2636. INTEGER , INTENT(IN) :: Count
  2637. INTEGER , INTENT(OUT) :: Status
  2638. CHARACTER(len=1000) :: tmpstr(1000)
  2639. INTEGER :: idx
  2640. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_td_logical')
  2641. if (fileinfo(DataHandle)%committed) then
  2642. do idx = 1,Count
  2643. write(tmpstr(idx),'(G17.10)')Data(idx)
  2644. enddo
  2645. CALL gr2_build_string (td_output(DataHandle), &
  2646. trim(DateStr)//';'//trim(Element), tmpstr, &
  2647. Count, Status)
  2648. endif
  2649. RETURN
  2650. END SUBROUTINE ext_gr2_put_dom_td_logical
  2651. !*****************************************************************************
  2652. SUBROUTINE ext_gr2_put_dom_td_char ( DataHandle,Element, DateStr, Data, &
  2653. Status )
  2654. USE gr2_data_info
  2655. IMPLICIT NONE
  2656. #include "wrf_status_codes.h"
  2657. INTEGER , INTENT(IN) :: DataHandle
  2658. CHARACTER*(*) :: Element
  2659. CHARACTER*(*) :: DateStr
  2660. CHARACTER(len=*), INTENT(IN) :: Data
  2661. INTEGER , INTENT(OUT) :: Status
  2662. CHARACTER(len=1000) :: tmpstr(1)
  2663. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_td_char')
  2664. if (fileinfo(DataHandle)%committed) then
  2665. write(tmpstr(1),*)Data
  2666. CALL gr2_build_string (td_output(DataHandle), &
  2667. trim(DateStr)//';'//trim(Element), tmpstr, &
  2668. 1, Status)
  2669. endif
  2670. RETURN
  2671. END SUBROUTINE ext_gr2_put_dom_td_char
  2672. !*****************************************************************************
  2673. SUBROUTINE ext_gr2_put_dom_td_double ( DataHandle,Element, DateStr, Data, &
  2674. Count, Status )
  2675. USE gr2_data_info
  2676. IMPLICIT NONE
  2677. #include "wrf_status_codes.h"
  2678. INTEGER , INTENT(IN) :: DataHandle
  2679. CHARACTER*(*) , INTENT(IN) :: Element
  2680. CHARACTER*(*) , INTENT(IN) :: DateStr
  2681. real*8 , INTENT(IN) :: Data(*)
  2682. INTEGER , INTENT(IN) :: Count
  2683. INTEGER , INTENT(OUT) :: Status
  2684. CHARACTER(len=1000) :: tmpstr(1000)
  2685. INTEGER :: idx
  2686. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_td_double')
  2687. if (fileinfo(DataHandle)%committed) then
  2688. do idx = 1,Count
  2689. write(tmpstr(idx),'(G17.10)')Data(idx)
  2690. enddo
  2691. CALL gr2_build_string (td_output(DataHandle), &
  2692. trim(DateStr)//';'//trim(Element), tmpstr, &
  2693. Count, Status)
  2694. endif
  2695. RETURN
  2696. END SUBROUTINE ext_gr2_put_dom_td_double
  2697. !*****************************************************************************
  2698. SUBROUTINE ext_gr2_put_dom_td_real ( DataHandle,Element, DateStr, Data, &
  2699. Count, Status )
  2700. USE gr2_data_info
  2701. IMPLICIT NONE
  2702. #include "wrf_status_codes.h"
  2703. INTEGER , INTENT(IN) :: DataHandle
  2704. CHARACTER*(*) :: Element
  2705. CHARACTER*(*) :: DateStr
  2706. real , INTENT(IN) :: Data(*)
  2707. INTEGER , INTENT(IN) :: Count
  2708. INTEGER , INTENT(OUT) :: Status
  2709. CHARACTER(len=1000) :: tmpstr(1000)
  2710. INTEGER :: idx
  2711. call wrf_debug ( DEBUG , 'Entering ext_gr2_put_dom_td_real')
  2712. if (fileinfo(DataHandle)%committed) then
  2713. do idx = 1,Count
  2714. write(tmpstr(idx),'(G17.10)')Data(idx)
  2715. enddo
  2716. CALL gr2_build_string (td_output(DataHandle), &
  2717. trim(DateStr)//';'//trim(Element), tmpstr, &
  2718. Count, Status)
  2719. endif
  2720. RETURN
  2721. END SUBROUTINE ext_gr2_put_dom_td_real
  2722. !******************************************************************************
  2723. !* End of put_dom_td_* routines
  2724. !******************************************************************************
  2725. SUBROUTINE gr2_get_new_handle(DataHandle)
  2726. USE gr2_data_info
  2727. IMPLICIT NONE
  2728. INTEGER , INTENT(OUT) :: DataHandle
  2729. INTEGER :: i
  2730. DataHandle = -1
  2731. do i=firstFileHandle, maxFileHandles
  2732. if (.NOT. fileinfo(i)%used) then
  2733. DataHandle = i
  2734. fileinfo(i)%used = .true.
  2735. exit
  2736. endif
  2737. enddo
  2738. RETURN
  2739. END SUBROUTINE gr2_get_new_handle
  2740. !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
  2741. !*****************************************************************************
  2742. SUBROUTINE gr2_retrieve_data (MemoryOrder, MemoryStart, MemoryEnd, xsize, ysize, &
  2743. zsize, z, FieldType, Field, data)
  2744. IMPLICIT NONE
  2745. #include "wrf_io_flags.h"
  2746. character*(*) ,intent(in) :: MemoryOrder
  2747. integer ,intent(in) :: xsize, ysize, zsize
  2748. integer ,intent(in) :: z
  2749. integer,dimension(*) ,intent(in) :: MemoryStart, MemoryEnd
  2750. integer ,intent(in) :: FieldType
  2751. real ,intent(in), &
  2752. dimension( 1:1,MemoryStart(1):MemoryEnd(1), &
  2753. MemoryStart(2):MemoryEnd(2), &
  2754. MemoryStart(3):MemoryEnd(3) ) :: Field
  2755. real ,dimension(1:xsize,1:ysize),intent(inout) :: data
  2756. integer :: x, y, idx
  2757. integer, dimension(:,:), pointer :: mold
  2758. integer :: istat
  2759. integer :: dim1
  2760. ALLOCATE(mold(1:xsize,1:ysize), STAT=istat)
  2761. if (istat .ne. 0) then
  2762. print *,'Could not allocate space for mold, returning'
  2763. return
  2764. endif
  2765. !
  2766. ! Set the size of the first dimension of the data array (dim1) to xsize.
  2767. ! If the MemoryOrder is Z or z, dim1 is overridden below.
  2768. !
  2769. dim1 = xsize
  2770. SELECT CASE (MemoryOrder)
  2771. CASE ('XYZ')
  2772. data = Field(1,1:xsize,1:ysize,z)
  2773. CASE ('C')
  2774. data = Field(1,1:xsize,1:ysize,z)
  2775. CASE ('XZY')
  2776. data = Field(1,1:xsize,z,1:ysize)
  2777. CASE ('YXZ')
  2778. do x = 1,xsize
  2779. do y = 1,ysize
  2780. data(x,y) = Field(1,y,x,z)
  2781. enddo
  2782. enddo
  2783. CASE ('YZX')
  2784. do x = 1,xsize
  2785. do y = 1,ysize
  2786. data(x,y) = Field(1,y,z,x)
  2787. enddo
  2788. enddo
  2789. CASE ('ZXY')
  2790. data = Field(1,z,1:xsize,1:ysize)
  2791. CASE ('ZYX')
  2792. do x = 1,xsize
  2793. do y = 1,ysize
  2794. data(x,y) = Field(1,z,y,x)
  2795. enddo
  2796. enddo
  2797. CASE ('XY')
  2798. data = Field(1,1:xsize,1:ysize,1)
  2799. CASE ('YX')
  2800. do x = 1,xsize
  2801. do y = 1,ysize
  2802. data(x,y) = Field(1,y,x,1)
  2803. enddo
  2804. enddo
  2805. CASE ('XSZ')
  2806. do x = 1,xsize
  2807. do y = 1,ysize
  2808. data(x,y) = Field(1,y,z,x)
  2809. enddo
  2810. enddo
  2811. CASE ('XEZ')
  2812. do x = 1,xsize
  2813. do y = 1,ysize
  2814. data(x,y) = Field(1,y,z,x)
  2815. enddo
  2816. enddo
  2817. CASE ('YSZ')
  2818. do x = 1,xsize
  2819. do y = 1,ysize
  2820. data(x,y) = Field(1,x,z,y)
  2821. enddo
  2822. enddo
  2823. CASE ('YEZ')
  2824. do x = 1,xsize
  2825. do y = 1,ysize
  2826. data(x,y) = Field(1,x,z,y)
  2827. enddo
  2828. enddo
  2829. CASE ('XS')
  2830. do x = 1,xsize
  2831. do y = 1,ysize
  2832. data(x,y) = Field(1,y,x,1)
  2833. enddo
  2834. enddo
  2835. CASE ('XE')
  2836. do x = 1,xsize
  2837. do y = 1,ysize
  2838. data(x,y) = Field(1,y,x,1)
  2839. enddo
  2840. enddo
  2841. CASE ('YS')
  2842. do x = 1,xsize
  2843. do y = 1,ysize
  2844. data(x,y) = Field(1,x,y,1)
  2845. enddo
  2846. enddo
  2847. CASE ('YE')
  2848. do x = 1,xsize
  2849. do y = 1,ysize
  2850. data(x,y) = Field(1,x,y,1)
  2851. enddo
  2852. enddo
  2853. CASE ('Z')
  2854. data(1:zsize,1) = Field(1,1:zsize,1,1)
  2855. dim1 = zsize
  2856. CASE ('z')
  2857. data(1:zsize,1) = Field(1,zsize:1,1,1)
  2858. dim1 = zsize
  2859. CASE ('0')
  2860. data(1,1) = Field(1,1,1,1)
  2861. END SELECT
  2862. !
  2863. ! Here, we convert any integer fields to real
  2864. !
  2865. if (FieldType == WRF_INTEGER) then
  2866. mold = 0
  2867. do idx=1,dim1
  2868. !
  2869. ! The parentheses around data(idx,:) are needed in order
  2870. ! to fix a bug with transfer with the xlf compiler on NCARs
  2871. ! IBM (bluesky).
  2872. !
  2873. data(idx,:)=transfer((data(idx,:)),mold)
  2874. enddo
  2875. endif
  2876. deallocate(mold)
  2877. return
  2878. end subroutine gr2_retrieve_data
  2879. !*****************************************************************************
  2880. SUBROUTINE gr2_get_levels(VarName, zidx, zsize, soil_layers, vert_stag, &
  2881. fraction, vert_unit1, vert_unit2, vert_sclFctr1, vert_sclFctr2, &
  2882. level1, level2)
  2883. use gr2_data_info
  2884. IMPLICIT NONE
  2885. integer :: zidx
  2886. integer :: zsize
  2887. logical :: soil_layers
  2888. logical :: vert_stag
  2889. logical :: fraction
  2890. integer :: vert_unit1, vert_unit2
  2891. integer :: vert_sclFctr1, vert_sclFctr2
  2892. integer :: level1
  2893. integer :: level2
  2894. character (LEN=*) :: VarName
  2895. ! Setup vert_unit, and vertical levels in grib units
  2896. if ((VarName .eq. 'LANDUSEF') .or. (VarName .eq. 'SOILCTOP') &
  2897. .or. (VarName .eq. 'SOILCBOT')) then
  2898. vert_unit1 = 105;
  2899. vert_unit2 = 255;
  2900. vert_sclFctr1 = 0
  2901. vert_sclFctr2 = 0
  2902. level1 = zidx
  2903. level2 = 0
  2904. else if ((zsize .gt. 1) .and. (.not. soil_layers) .and. (.not. fraction)) &
  2905. then
  2906. vert_unit1 = 111;
  2907. vert_unit2 = 255;
  2908. vert_sclFctr1 = 4
  2909. vert_sclFctr2 = 4
  2910. if (vert_stag) then
  2911. level1 = (10000*full_eta(zidx)+0.5)
  2912. else
  2913. level1 = (10000*half_eta(zidx)+0.5)
  2914. endif
  2915. level2 = 0
  2916. else
  2917. ! Set the vertical coordinate and level for soil and 2D fields
  2918. if (fraction) then
  2919. vert_unit1 = 105
  2920. vert_unit2 = 255
  2921. level1 = zidx
  2922. level2 = 0
  2923. vert_sclFctr1 = 0
  2924. vert_sclFctr2 = 0
  2925. else if (soil_layers) then
  2926. vert_unit1 = 106
  2927. vert_unit2 = 106
  2928. level1 = 100*(soil_depth(zidx) - 0.5*soil_thickness(zidx))+0.5
  2929. level2 = 100*(soil_depth(zidx) + 0.5*soil_thickness(zidx))+0.5
  2930. vert_sclFctr1 = 2
  2931. vert_sclFctr2 = 2
  2932. else if (VarName .eq. 'mu') then
  2933. vert_unit1 = 105
  2934. vert_unit2 = 255
  2935. level1 = 0
  2936. level2 = 0
  2937. vert_sclFctr1 = 0
  2938. vert_sclFctr2 = 0
  2939. else if ((VarName .eq. 'Q2') .or. (VarName .eq. 'TH2') .or. &
  2940. (VarName .eq. 'T2')) then
  2941. vert_unit1 = 103
  2942. vert_unit2 = 255
  2943. level1 = 2
  2944. level2 = 0
  2945. vert_sclFctr1 = 0
  2946. vert_sclFctr2 = 0
  2947. else if ((VarName .eq. 'Q10') .or. (VarName .eq. 'TH10') .or. &
  2948. (VarName .eq. 'U10') .or. (VarName .eq. 'V10')) then
  2949. vert_unit1 = 103
  2950. vert_unit2 = 255
  2951. level1 = 10
  2952. level2 = 0
  2953. vert_sclFctr1 = 0
  2954. vert_sclFctr2 = 0
  2955. else
  2956. vert_unit1 = 1
  2957. vert_unit2 = 255
  2958. level1 = 0
  2959. level2 = 0
  2960. vert_sclFctr1 = 0
  2961. vert_sclFctr2 = 0
  2962. endif
  2963. endif
  2964. end SUBROUTINE gr2_get_levels
  2965. !*****************************************************************************
  2966. subroutine gr2_create_w(StartDate, cgrib, lcgrib, production_status, Disc, &
  2967. center, subcenter, MasterTblV, LocalTblV, ierr, msg)
  2968. implicit none
  2969. character*24 ,intent(in) :: StartDate
  2970. character*(*),intent(inout) :: cgrib
  2971. integer ,intent(in) :: lcgrib
  2972. integer ,intent(in) :: production_status
  2973. integer ,intent(out) :: ierr
  2974. character*(*),intent(out) :: msg
  2975. integer , dimension(13) :: listsec1
  2976. integer , dimension(2) :: listsec0
  2977. integer :: slen
  2978. integer , intent(in) :: Disc, center, subcenter, MasterTblV, LocalTblV
  2979. !
  2980. ! Create the grib message
  2981. !
  2982. listsec0(1) = Disc ! Discipline (Table 0.0)
  2983. listsec0(2) = 2 ! Grib edition number
  2984. listsec1(1) = center ! Id of Originating Center (255 for missing)
  2985. listsec1(2) = subcenter ! Id of originating sub-center (255 for missing)
  2986. listsec1(3) = MasterTblV ! Master Table Version #
  2987. listsec1(4) = LocalTblV ! Local table version #
  2988. listsec1(5) = 1 ! Significance of reference time, 1 indicates start of forecast
  2989. READ(StartDate(1:4), '(I4)') listsec1(6) ! Year of reference
  2990. READ(StartDate(6:7), '(I2)') listsec1(7) ! Month of reference
  2991. READ(StartDate(9:10), '(I2)') listsec1(8) ! Day of reference
  2992. slen = LEN(StartDate)
  2993. if (slen.GE.13) then
  2994. read(StartDate(12:13),'(I2)') listsec1(9)
  2995. else
  2996. listsec1(9) = 0
  2997. endif
  2998. if (slen.GE.16) then
  2999. read(StartDate(15:16),'(I2)') listsec1(10)
  3000. else
  3001. listsec1(10) = 0
  3002. endif
  3003. if (slen.GE.19) then
  3004. read(StartDate(18:19),'(I2)') listsec1(11)
  3005. else
  3006. listsec1(11) = 0
  3007. end if
  3008. listsec1(12) = production_status ! Production status of data
  3009. listsec1(13) = 1 ! Type of data (1 indicates forecast products)
  3010. call gribcreate(cgrib,lcgrib,listsec0,listsec1,ierr)
  3011. if (ierr .ne. 0) then
  3012. write(msg,*) 'gribcreate failed with ierr: ',ierr
  3013. else
  3014. msg = ''
  3015. endif
  3016. end SUBROUTINE gr2_create_w
  3017. !*****************************************************************************
  3018. subroutine gr2_addgrid_w(cgrib, lcgrib, central_lat, central_lon, wrf_projection, &
  3019. latin1, latin2, nx, ny, dx, dy, center_lat, center_lon, ierr,msg)
  3020. implicit none
  3021. character*(*) ,intent(inout) :: cgrib
  3022. integer ,intent(in) :: lcgrib
  3023. real ,intent(in) :: central_lat
  3024. real ,intent(in) :: central_lon
  3025. integer ,intent(in) :: wrf_projection
  3026. real ,intent(in) :: latin1
  3027. real ,intent(in) :: latin2
  3028. integer ,intent(in) :: nx
  3029. integer ,intent(in) :: ny
  3030. real ,intent(in) :: dx
  3031. real ,intent(in) :: dy
  3032. real ,intent(in) :: center_lat
  3033. real ,intent(in) :: center_lon
  3034. integer ,intent(out) :: ierr
  3035. character*(*) ,intent(out) :: msg
  3036. integer, dimension(5) :: igds
  3037. integer, parameter :: igdstmplen = 25
  3038. integer, dimension(igdstmplen) :: igdstmpl
  3039. integer, parameter :: idefnum = 0
  3040. integer, dimension(idefnum) :: ideflist
  3041. real :: LLLa, LLLo, URLa, URLo
  3042. real :: incrx, incry
  3043. real, parameter :: deg_to_microdeg = 1e6
  3044. real, parameter :: km_to_mm = 1e6
  3045. real, parameter :: km_to_m = 1e3
  3046. real, parameter :: DEG_TO_RAD = PI/180
  3047. real, parameter :: RAD_TO_DEG = 180/PI
  3048. real, parameter :: ERADIUS = 6370.0
  3049. igds(1) = 0 ! Source of grid definition
  3050. igds(2) = nx*ny ! Number of points in grid
  3051. igds(3) = 0 !
  3052. igds(4) = 0
  3053. ! Here, setup the parameters that are common to all WRF projections
  3054. igdstmpl(1) = 1 ! Shape of earth (1 for spherical with specified radius)
  3055. igdstmpl(2) = 0 ! Scale factor for earth radius
  3056. igdstmpl(3) = ERADIUS*km_to_m ! Radius of earth
  3057. igdstmpl(4) = 0 ! Scale factor for major axis
  3058. igdstmpl(5) = 0 ! Major axis
  3059. igdstmpl(6) = 0 ! Scale factor for minor axis
  3060. igdstmpl(7) = 0 ! Minor axis
  3061. igdstmpl(8) = nx ! Number of points along x axis
  3062. igdstmpl(9) = ny ! Number of points along y axis
  3063. !
  3064. ! Setup increments in "x" and "y" direction. For LATLON projection
  3065. ! increments need to be in degrees. For all other projections,
  3066. ! increments are in km.
  3067. !
  3068. if ((wrf_projection .eq. WRF_LATLON) &
  3069. .or. (wrf_projection .eq. WRF_CASSINI)) then
  3070. incrx = (dx/ERADIUS) * RAD_TO_DEG
  3071. incry = (dy/ERADIUS) * RAD_TO_DEG
  3072. else
  3073. incrx = dx
  3074. incry = dy
  3075. endif
  3076. ! Latitude and longitude of first (i.e., lower left) grid point
  3077. call get_ll_latlon(central_lat, central_lon, wrf_projection, &
  3078. latin1, latin2, nx, ny, incrx, incry, center_lat, center_lon, &
  3079. LLLa, LLLo, URLa, URLo, ierr);
  3080. select case (wrf_projection)
  3081. case(WRF_LATLON,WRF_CASSINI)
  3082. igds(5) = 0
  3083. igdstmpl(10) = 0 ! Basic Angle of init projection (not important to us)
  3084. igdstmpl(11) = 0 ! Subdivision of basic angle
  3085. igdstmpl(12) = LLLa*deg_to_microdeg
  3086. igdstmpl(13) = LLLo*deg_to_microdeg
  3087. call gr2_convert_lon(igdstmpl(13))
  3088. igdstmpl(14) = 128 ! Resolution and component flags
  3089. igdstmpl(15) = URLa*deg_to_microdeg
  3090. igdstmpl(16) = URLo*deg_to_microdeg
  3091. call gr2_convert_lon(igdstmpl(16))
  3092. ! Warning, the following assumes that dx and dy are valid at the equator.
  3093. ! It is not clear in WRF where dx and dy are valid for latlon projections
  3094. igdstmpl(17) = incrx*deg_to_microdeg ! i-direction increment in micro degs
  3095. igdstmpl(18) = incry*deg_to_microdeg ! j-direction increment in micro degs
  3096. igdstmpl(19) = 64 ! Scanning mode
  3097. case(WRF_MERCATOR)
  3098. igds(5) = 10
  3099. igdstmpl(10) = LLLa*deg_to_microdeg
  3100. igdstmpl(11) = LLLo*deg_to_microdeg
  3101. call gr2_convert_lon(igdstmpl(11))
  3102. igdstmpl(12) = 128 ! Resolution and component flags
  3103. igdstmpl(13) = latin1*deg_to_microdeg ! "True" latitude
  3104. igdstmpl(14) = URLa*deg_to_microdeg
  3105. igdstmpl(15) = URLo*deg_to_microdeg
  3106. call gr2_convert_lon(igdstmpl(15))
  3107. igdstmpl(16) = 64 ! Scanning mode
  3108. igdstmpl(17) = 0 ! Orientation of grid between i-direction and equator
  3109. igdstmpl(18) = dx*km_to_mm ! i-direction increment
  3110. igdstmpl(19) = dy*km_to_mm ! j-direction increment
  3111. case(WRF_LAMBERT)
  3112. igds(5) = 30
  3113. igdstmpl(10) = LLLa*deg_to_microdeg
  3114. igdstmpl(11) = LLLo*deg_to_microdeg
  3115. call gr2_convert_lon(igdstmpl(11))
  3116. igdstmpl(12) = 128 ! Resolution and component flag
  3117. igdstmpl(13) = latin1*deg_to_microdeg ! Latitude where Dx and Dy are specified
  3118. igdstmpl(14) = central_lon*deg_to_microdeg
  3119. call gr2_convert_lon(igdstmpl(14))
  3120. igdstmpl(15) = dx*km_to_mm ! x-dimension grid-spacing in units of m^-3
  3121. igdstmpl(16) = dy*km_to_mm
  3122. if (center_lat .lt. 0) then
  3123. igdstmpl(17) = 1
  3124. else
  3125. igdstmpl(17) = 0
  3126. endif
  3127. igdstmpl(18) = 64 ! Scanning mode
  3128. igdstmpl(19) = latin1*deg_to_microdeg
  3129. igdstmpl(20) = latin2*deg_to_microdeg
  3130. igdstmpl(21) = -90*deg_to_microdeg
  3131. igdstmpl(22) = central_lon*deg_to_microdeg
  3132. call gr2_convert_lon(igdstmpl(22))
  3133. case(WRF_POLAR_STEREO)
  3134. igds(5) = 20
  3135. igdstmpl(10) = LLLa*deg_to_microdeg
  3136. igdstmpl(11) = LLLo*deg_to_microdeg
  3137. call gr2_convert_lon(igdstmpl(11))
  3138. igdstmpl(12) = 128 ! Resolution and component flag
  3139. igdstmpl(13) = latin1*deg_to_microdeg ! Latitude where Dx and Dy are specified
  3140. igdstmpl(14) = central_lon*deg_to_microdeg
  3141. call gr2_convert_lon(igdstmpl(14))
  3142. igdstmpl(15) = dx*km_to_mm ! x-dimension grid-spacing in units of m^-3
  3143. igdstmpl(16) = dy*km_to_mm
  3144. if (center_lat .lt. 0) then
  3145. igdstmpl(17) = 1
  3146. else
  3147. igdstmpl(17) = 0
  3148. endif
  3149. igdstmpl(18) = 64 ! Scanning mode
  3150. case default
  3151. write(msg,*) 'invalid WRF projection: ',wrf_projection
  3152. ierr = -1
  3153. return
  3154. end select
  3155. call addgrid(cgrib,lcgrib,igds,igdstmpl,igdstmplen,ideflist,idefnum,ierr)
  3156. if (ierr .ne. 0) then
  3157. write(msg,*) 'addgrid failed with ierr: ',ierr
  3158. else
  3159. msg = ''
  3160. endif
  3161. end subroutine gr2_addgrid_w
  3162. !*****************************************************************************
  3163. subroutine gr2_addfield_w(cgrib, lcgrib, VarName, parmcat, parmnum, DecScl, &
  3164. BinScl, fcst_secs, vert_unit1, vert_unit2, vert_sclFctr1, vert_sclFctr2, &
  3165. numlevels, levels, ngrdpts, background_proc_id, forecast_proc_id, &
  3166. compression, fld, ierr, msg)
  3167. implicit none
  3168. character*(*) ,intent(inout) :: cgrib
  3169. integer ,intent(in) :: lcgrib
  3170. character (LEN=*) ,intent(in) :: VarName
  3171. integer ,intent(in) :: parmcat,parmnum,DecScl,BinScl
  3172. real ,intent(in) :: fcst_secs
  3173. integer ,intent(in) :: vert_unit1, vert_unit2
  3174. integer ,intent(in) :: vert_sclFctr1, vert_sclFctr2
  3175. integer ,intent(in) :: numlevels
  3176. integer, dimension(*) ,intent(in) :: levels
  3177. integer ,intent(in) :: ngrdpts
  3178. real ,intent(in) :: fld(ngrdpts)
  3179. integer ,intent(in) :: background_proc_id
  3180. integer ,intent(in) :: forecast_proc_id
  3181. integer ,intent(in) :: compression
  3182. integer ,intent(out) :: ierr
  3183. character*(*) ,intent(out) :: msg
  3184. integer :: ipdsnum
  3185. integer, parameter :: ipdstmplen = 15
  3186. integer, dimension(ipdstmplen) :: ipdstmpl
  3187. integer :: numcoord
  3188. integer, dimension(numlevels) :: coordlist
  3189. integer :: idrsnum
  3190. integer, parameter :: idrstmplen = 7
  3191. integer, dimension(idrstmplen) :: idrstmpl
  3192. integer :: ibmap
  3193. integer, dimension(1) :: bmap
  3194. if (numlevels .gt. 2) then
  3195. ipdsnum = 1000 ! Product definition tmplate (1000 for cross-sxn)
  3196. else
  3197. ipdsnum = 0 ! Product definition template (0 for horiz grid)
  3198. endif
  3199. ipdstmpl(1) = parmcat ! Parameter category
  3200. ipdstmpl(2) = parmnum ! Parameter number
  3201. ipdstmpl(3) = 2 ! Type of generating process (2 for forecast)
  3202. ipdstmpl(4) = background_proc_id ! Background generating process id
  3203. ipdstmpl(5) = forecast_proc_id ! Analysis or forecast generating process id
  3204. ipdstmpl(6) = 0 ! Data cutoff period (Hours)
  3205. ipdstmpl(7) = 0 ! Data cutoff period (minutes)
  3206. ipdstmpl(8) = 13 ! Time range indicator (13 for seconds)
  3207. ipdstmpl(9) = NINT(fcst_secs) ! Forecast time
  3208. if (ipdsnum .eq. 1000) then
  3209. numcoord = numlevels
  3210. coordlist = levels(1:numlevels)
  3211. !
  3212. ! Set Data Representation templ (Use 0 for vertical cross sections,
  3213. ! since there seems to be a bug in g2lib for JPEG2000 and PNG)
  3214. !
  3215. idrsnum = 0
  3216. else if (ipdsnum .eq. 0) then
  3217. ipdstmpl(10) = vert_unit1 ! Type of first surface (111 for Eta level)
  3218. ipdstmpl(11) = vert_sclFctr1 ! Scale factor for 1st surface
  3219. ipdstmpl(12) = levels(1) ! First fixed surface
  3220. ipdstmpl(13) = vert_unit2 ! Type of second fixed surface
  3221. ipdstmpl(14) = vert_sclFctr2 ! Scale factor for 2nd surface
  3222. if (numlevels .eq. 2) then
  3223. ipdstmpl(15) = levels(2)
  3224. else
  3225. ipdstmpl(15) = 0
  3226. endif
  3227. numcoord = 0
  3228. coordlist(1) = 0
  3229. ! Set Data Representation templ (40 for JPEG2000, 41 for PNG)
  3230. idrsnum = compression
  3231. endif
  3232. if (idrsnum == 40) then ! JPEG 2000
  3233. idrstmpl(1) = 255 ! Reference value - ignored on input
  3234. idrstmpl(2) = BinScl ! Binary scale factor
  3235. idrstmpl(3) = DecScl ! Decimal scale factor
  3236. idrstmpl(4) = 0 ! number of bits for each data value - ignored on input
  3237. idrstmpl(5) = 0 ! Original field type - ignored on input
  3238. idrstmpl(6) = 0 ! 0 for lossless compression
  3239. idrstmpl(7) = 255 ! Desired compression ratio if idrstmpl(6) != 0
  3240. else if (idrsnum == 41) then ! PNG
  3241. idrstmpl(1) = 255 ! Reference value - ignored on input
  3242. idrstmpl(2) = BinScl ! Binary scale factor
  3243. idrstmpl(3) = DecScl ! Decimal scale factor
  3244. idrstmpl(4) = 0 ! number of bits for each data value - ignored on input
  3245. idrstmpl(5) = 0 ! Original field type - ignored on input
  3246. else if (idrsnum == 0) then! Simple packing
  3247. idrstmpl(1) = 255 ! Reference value - ignored on input
  3248. idrstmpl(2) = BinScl ! Binary scale factor
  3249. idrstmpl(3) = DecScl ! Decimal scale factor
  3250. idrstmpl(4) = 0 ! number of bits for each data value - ignored on input
  3251. idrstmpl(5) = 0 ! Original field type - ignored on input
  3252. else
  3253. write (msg,*) 'addfield failed because Data Representation template',&
  3254. idrsnum,' is invalid'
  3255. ierr = 1
  3256. return
  3257. endif
  3258. ibmap = 255 ! Flag for bitmap
  3259. call addfield(cgrib, lcgrib, ipdsnum, ipdstmpl, ipdstmplen, coordlist, &
  3260. numcoord, idrsnum, idrstmpl, idrstmplen, fld, ngrdpts, ibmap, &
  3261. bmap, ierr)
  3262. if (ierr .ne. 0) then
  3263. write(msg,*) 'addfield failed with ierr: ',ierr
  3264. else
  3265. msg = ''
  3266. endif
  3267. end subroutine gr2_addfield_w
  3268. !*****************************************************************************
  3269. subroutine gr2_fill_local_use(DataHandle,string,VarName,fcsts,msg,status)
  3270. use gr2_data_info
  3271. IMPLICIT NONE
  3272. #include "wrf_status_codes.h"
  3273. integer, intent(in) :: DataHandle
  3274. character*(*) ,intent(inout) :: string
  3275. character*(*) ,intent(in) :: VarName
  3276. integer :: center, subcenter, MasterTblV, LocalTblV, &
  3277. Disc, Category, ParmNum, DecScl, BinScl
  3278. integer ,intent(out) :: status
  3279. character*(*) ,intent(out) :: msg
  3280. integer , parameter :: lcgrib = 1000000
  3281. character (lcgrib) :: cgrib
  3282. real, dimension(1,1) :: data
  3283. integer :: lengrib
  3284. integer :: lcsec2
  3285. integer :: fcsts
  3286. integer :: bytes_written
  3287. !
  3288. ! Set data to a default dummy value.
  3289. !
  3290. data = 1.0
  3291. !
  3292. ! This statement prevents problems when calling addlocal in the grib2
  3293. ! library. Basically, if addlocal is called with an empty string, it
  3294. ! will be encoded correctly by the grib2 routine, but the grib2 routines
  3295. ! that read the data (i.e., getgb2) will segfault. This prevents that
  3296. ! segfault.
  3297. !
  3298. if (string .eq. '') string = 'none'
  3299. CALL get_parminfo(VarName, center, subcenter, MasterTblV, &
  3300. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl, status)
  3301. if (status .ne. 0) then
  3302. write(msg,*) 'Could not find parameter for '// &
  3303. trim(VarName)//' Skipping output of '//trim(VarName)
  3304. call wrf_message(trim(msg))
  3305. Status = WRF_GRIB2_ERR_GRIB2MAP
  3306. return
  3307. endif
  3308. !
  3309. ! Create the indicator and identification sections (sections 0 and 1)
  3310. !
  3311. CALL gr2_create_w(StartDate, cgrib, lcgrib, production_status, Disc, &
  3312. center, subcenter, MasterTblV, LocalTblV, status, msg)
  3313. if (status .ne. 0) then
  3314. call wrf_message(trim(msg))
  3315. Status = WRF_GRIB2_ERR_GRIBCREATE
  3316. return
  3317. endif
  3318. !
  3319. ! Add the local use section
  3320. !
  3321. lcsec2 = len_trim(string)
  3322. call addlocal(cgrib,lcgrib,string,lcsec2,status)
  3323. if (status .ne. 0) then
  3324. call wrf_message(trim(msg))
  3325. Status = WRF_GRIB2_ERR_ADDLOCAL
  3326. return
  3327. endif
  3328. !
  3329. ! Add the grid definition section (section 3) using a 1x1 grid
  3330. !
  3331. call gr2_addgrid_w(cgrib, lcgrib, center_lat, proj_central_lon, &
  3332. wrf_projection, truelat1, truelat2, 1, 1, dx, dy, &
  3333. center_lat, center_lon, status, msg)
  3334. if (status .ne. 0) then
  3335. call wrf_message(trim(msg))
  3336. Status = WRF_GRIB2_ERR_ADDGRIB
  3337. return
  3338. endif
  3339. !
  3340. ! Add the Product Definition, Data representation, bitmap
  3341. ! and data sections (sections 4-7)
  3342. !
  3343. call gr2_addfield_w(cgrib, lcgrib, VarName, Category, ParmNum, DecScl, &
  3344. BinScl, fcsts, 1, 255, 0, 0, 1, 0, 1, &
  3345. background_proc_id, forecast_proc_id, compression, data, status, msg)
  3346. if (status .ne. 0) then
  3347. call wrf_message(trim(msg))
  3348. Status = WRF_GRIB2_ERR_ADDFIELD
  3349. return
  3350. endif
  3351. !
  3352. ! Close out the message
  3353. !
  3354. call gribend(cgrib,lcgrib,lengrib,status)
  3355. if (status .ne. 0) then
  3356. write(msg,*) 'gribend failed with status: ',status
  3357. call wrf_message(trim(msg))
  3358. Status = WRF_GRIB2_ERR_GRIBEND
  3359. return
  3360. endif
  3361. !
  3362. ! Write the data to the file
  3363. !
  3364. call bawrite(DataHandle, -1, lengrib, bytes_written, cgrib)
  3365. !! call write_file_n(fileinfo(DataHandle)%FileFd, cgrib, lengrib, status)
  3366. if (bytes_written .ne. lengrib) then
  3367. write(msg,*) '2 Error writing cgrib to file, wrote: ', &
  3368. bytes_written, ' bytes. Tried to write ', lengrib, ' bytes'
  3369. call wrf_message(trim(msg))
  3370. Status = WRF_GRIB2_ERR_WRITE
  3371. return
  3372. endif
  3373. ! Set string back to the original blank value
  3374. if (string .eq. '') string = ''
  3375. return
  3376. end subroutine gr2_fill_local_use
  3377. !*****************************************************************************
  3378. !
  3379. ! Set longitude to be in the range of 0-360 degrees.
  3380. !
  3381. !*****************************************************************************
  3382. subroutine gr2_convert_lon(value)
  3383. IMPLICIT NONE
  3384. integer, intent(inout) :: value
  3385. real, parameter :: deg_to_microdeg = 1e6
  3386. do while (value .lt. 0)
  3387. value = value + 360*deg_to_microdeg
  3388. enddo
  3389. do while (value .gt. 360*deg_to_microdeg)
  3390. value = value - 360*deg_to_microdeg
  3391. enddo
  3392. end subroutine gr2_convert_lon
  3393. !*****************************************************************************
  3394. !
  3395. ! Add a time to the list of times
  3396. !
  3397. !*****************************************************************************
  3398. subroutine gr2_add_time(DataHandle,addTime)
  3399. USE gr2_data_info
  3400. IMPLICIT NONE
  3401. integer :: DataHandle
  3402. character (len=*) :: addTime
  3403. integer :: idx
  3404. logical :: already_have = .false.
  3405. logical :: swap
  3406. character (len=len(addTime)) :: tmp
  3407. character (DateStrLen), dimension(:),pointer :: tmpTimes(:)
  3408. integer,parameter :: allsize = 50
  3409. integer :: ierr
  3410. already_have = .false.
  3411. do idx = 1,fileinfo(DataHandle)%NumberTimes
  3412. if (addTime .eq. fileinfo(DataHandle)%Times(idx)) then
  3413. already_have = .true.
  3414. endif
  3415. enddo
  3416. if (.not. already_have) then
  3417. fileinfo(DataHandle)%NumberTimes = fileinfo(DataHandle)%NumberTimes + 1
  3418. if (fileinfo(DataHandle)%NumberTimes .gt. &
  3419. fileinfo(DataHandle)%sizeAllocated) then
  3420. if (fileinfo(DataHandle)%NumberTimes .eq. 1) then
  3421. if (allocated(fileinfo(DataHandle)%Times)) &
  3422. deallocate(fileinfo(DataHandle)%Times)
  3423. allocate(fileinfo(DataHandle)%Times(allsize), stat = ierr)
  3424. if (ierr .ne. 0) then
  3425. call wrf_message('Could not allocate space for Times 1, exiting')
  3426. stop
  3427. endif
  3428. fileinfo(DataHandle)%sizeAllocated = allsize
  3429. else
  3430. allocate(tmpTimes(fileinfo(DataHandle)%NumberTimes), stat=ierr)
  3431. tmpTimes = &
  3432. fileinfo(DataHandle)%Times(1:fileinfo(DataHandle)%NumberTimes)
  3433. deallocate(fileinfo(DataHandle)%Times)
  3434. allocate(&
  3435. fileinfo(DataHandle)%Times(fileinfo(DataHandle)%sizeAllocated+allsize), stat=ierr)
  3436. if (ierr .ne. 0) then
  3437. call wrf_message('Could not allocate space for Times 2, exiting')
  3438. stop
  3439. endif
  3440. fileinfo(DataHandle)%Times(1:fileinfo(DataHandle)%NumberTimes) = &
  3441. tmpTimes
  3442. deallocate(tmpTimes)
  3443. endif
  3444. endif
  3445. fileinfo(DataHandle)%Times(fileinfo(DataHandle)%NumberTimes) = addTime
  3446. ! Sort the Times array
  3447. swap = .true.
  3448. do while (swap)
  3449. swap = .false.
  3450. do idx = 1,fileinfo(DataHandle)%NumberTimes - 1
  3451. if (fileinfo(DataHandle)%Times(idx) .gt. fileinfo(DataHandle)%Times(idx+1)) then
  3452. tmp = fileinfo(DataHandle)%Times(idx)
  3453. fileinfo(DataHandle)%Times(idx) = fileinfo(DataHandle)%Times(idx+1)
  3454. fileinfo(DataHandle)%Times(idx+1) = tmp
  3455. swap = .true.
  3456. endif
  3457. enddo
  3458. enddo
  3459. endif
  3460. return
  3461. end subroutine gr2_add_time
  3462. !*****************************************************************************
  3463. !
  3464. ! Fill an array of levels
  3465. !
  3466. !*****************************************************************************
  3467. subroutine gr2_fill_levels(DataHandle,VarName,levels,ierr)
  3468. USE gr2_data_info
  3469. USE grib_mod
  3470. IMPLICIT NONE
  3471. #include "wrf_status_codes.h"
  3472. integer :: DataHandle
  3473. character (len=*) :: VarName
  3474. REAL,DIMENSION(*) :: levels
  3475. integer :: ierr
  3476. integer :: JIDS(JIDSSIZE), JPDTN, JPDT(JPDTSIZE), JGDTN, &
  3477. JGDT(JGDTSIZE)
  3478. type(gribfield) :: gfld
  3479. integer :: status, fields_to_skip
  3480. logical :: unpack
  3481. integer :: center, subcenter, MasterTblV, LocalTblV, &
  3482. Disc, Category, ParmNum, DecScl, BinScl
  3483. CHARACTER (LEN=maxMsgSize) :: msg
  3484. CALL get_parminfo(VarName, center, subcenter, MasterTblV, &
  3485. LocalTblV, Disc, Category, ParmNum, DecScl, BinScl, status)
  3486. if (status .ne. 0) then
  3487. write(msg,*) 'Could not find parameter for '// &
  3488. trim(VarName)//' Skipping output of '//trim(VarName)
  3489. call wrf_message(trim(msg))
  3490. ierr = -1
  3491. return
  3492. endif
  3493. !
  3494. ! First, set all values to wild, then specify necessary values
  3495. !
  3496. call gr2_g2lib_wildcard(JIDS, JPDT, JGDT)
  3497. JIDS(1) = center
  3498. JIDS(2) = subcenter
  3499. JIDS(3) = MasterTblV
  3500. JIDS(4) = LocalTblV
  3501. JIDS(5) = 1 ! Indicates that time is "Start of Forecast"
  3502. JIDS(13) = 1 ! Type of processed data (1 for forecast products)
  3503. JPDTN = 1000 ! Product definition template number
  3504. JPDT(1) = Category
  3505. JPDT(2) = ParmNum
  3506. JPDT(3) = 2 ! Generating process id
  3507. JGDTN = -1 ! Indicates that any Grid Display Template is a match
  3508. UNPACK = .TRUE. ! Unpack bitmap and data values
  3509. fields_to_skip = 0
  3510. CALL GETGB2(DataHandle, 0, fields_to_skip, -1, Disc, JIDS, JPDTN, &
  3511. JPDT, JGDTN, JGDT, UNPACK, fileinfo(DataHandle)%recnum, &
  3512. gfld, status)
  3513. if (status .eq. 99) then
  3514. write(msg,*)'Could not find field '//trim(VarName)//&
  3515. ' continuing.'
  3516. call wrf_message(trim(msg))
  3517. ierr = -1
  3518. return
  3519. else if (status .ne. 0) then
  3520. write(msg,*)'Retrieving scalar data field '//trim(VarName)//&
  3521. ' failed, continuing.'
  3522. call wrf_message(trim(msg))
  3523. ierr = -1
  3524. return
  3525. endif
  3526. levels(1:gfld%ndpts) = gfld%fld(1:gfld%ndpts)
  3527. ierr = 0
  3528. end subroutine gr2_fill_levels
  3529. !*****************************************************************************
  3530. !
  3531. ! Set values for search array arguments for getgb2 to missing.
  3532. !
  3533. !*****************************************************************************
  3534. subroutine gr2_g2lib_wildcard(JIDS, JPDT, JGDT)
  3535. USE gr2_data_info
  3536. integer :: JIDS(*), JPDT(*), JGDT(*)
  3537. do idx = 1,JIDSSIZE
  3538. JIDS(idx) = -9999
  3539. enddo
  3540. do idx=1,JPDTSIZE
  3541. JPDT(idx) = -9999
  3542. enddo
  3543. do idx = 1,JGDTSIZE
  3544. JGDT(idx) = -9999
  3545. enddo
  3546. return
  3547. end subroutine gr2_g2lib_wildcard
  3548. !*****************************************************************************
  3549. !
  3550. ! Retrieve a metadata value from the input string
  3551. !
  3552. !*****************************************************************************
  3553. subroutine gr2_get_metadata_value(instring, Key, Value, stat)
  3554. character(len=*),intent(in) :: instring
  3555. character(len=*),intent(in) :: Key
  3556. character(len=*),intent(out) :: Value
  3557. integer ,intent(out) :: stat
  3558. integer :: Key_pos, equals_pos, line_end
  3559. character :: lf
  3560. lf=char(10)
  3561. Value = 'abc'
  3562. !
  3563. ! Find Starting position of Key
  3564. !
  3565. Key_pos = index(instring, lf//' '//Key//' =')
  3566. if (Key_pos .eq. 0) then
  3567. stat = -1
  3568. return
  3569. endif
  3570. !
  3571. ! Find position of the "=" after the Key
  3572. !
  3573. equals_pos = index(instring(Key_pos:len(instring)), "=") + Key_pos
  3574. if (equals_pos .eq. Key_pos) then
  3575. stat = -1
  3576. return
  3577. endif
  3578. !
  3579. ! Find end of line
  3580. !
  3581. line_end = index(instring(equals_pos:len(instring)), lf) + equals_pos
  3582. !
  3583. ! Handle the case for the last line in the string
  3584. !
  3585. if (line_end .eq. equals_pos) then
  3586. line_end = len(trim(instring))
  3587. endif
  3588. !
  3589. ! Set value
  3590. !
  3591. if ( (equals_pos + 1) .le. (line_end - 2) ) then
  3592. Value = trim(adjustl(instring(equals_pos+1:line_end-2)))
  3593. else
  3594. Value = ""
  3595. endif
  3596. stat = 0
  3597. end subroutine gr2_get_metadata_value
  3598. !*****************************************************************************
  3599. !
  3600. ! Build onto a metadata string with the input value
  3601. !
  3602. !*****************************************************************************
  3603. SUBROUTINE gr2_build_string (string, Element, Value, Count, Status)
  3604. IMPLICIT NONE
  3605. #include "wrf_status_codes.h"
  3606. CHARACTER (LEN=*) , INTENT(INOUT) :: string
  3607. CHARACTER (LEN=*) , INTENT(IN) :: Element
  3608. CHARACTER (LEN=*) , INTENT(IN) :: Value(*)
  3609. INTEGER , INTENT(IN) :: Count
  3610. INTEGER , INTENT(OUT) :: Status
  3611. CHARACTER (LEN=2) :: lf
  3612. INTEGER :: IDX
  3613. lf=char(10)//' '
  3614. if (index(string,lf//Element//' =') .gt. 0) then
  3615. ! We do nothing, since we dont want to add the same variable twice.
  3616. else
  3617. if (len_trim(string) == 0) then
  3618. string = lf//Element//' = '
  3619. else
  3620. string = trim(string)//lf//Element//' = '
  3621. endif
  3622. do idx = 1,Count
  3623. if (idx > 1) then
  3624. string = trim(string)//','
  3625. endif
  3626. string = trim(string)//' '//trim(adjustl(Value(idx)))
  3627. enddo
  3628. endif
  3629. Status = WRF_NO_ERR
  3630. END SUBROUTINE gr2_build_string