gtool5 Fortran 90/95 ライブラリ 1.0.0-rc5
English
Loading...
Searching...
No Matches
gtdata_netcdf_internal.f90
Go to the documentation of this file.
1!>
2!> @file gtdata_netcdf_internal.f90
3!>
4!> @author Yasuhiro MORIKAWA, Eizi TOYODA
5!> @copyright Copyright (C) GFD Dennou Club, 2001-2026. All rights reserved. <br/>
6!> License is BSD-2-Clause. See [COPYRIGHT](@ref COPYRIGHT) in detail
7!>
8!> @en
9!> @brief Internal constants, variables, procedures used in "gtdata_netcdf"
10!> @enden
11!>
12!> @ja
13!> @brief gtdata_netcdf 内で使用される内部向け定数, 変数, 手続き群
14!> @endja
15!>
16
17!>
18!> @private
19!>
20!> @en
21!> @brief Internal constants, variables, procedures used in "gtdata_netcdf"
22!>
23!> This module provides the internal variable table (gdnctab) and
24!> procedures to manage it.
25!>
26!> | Procedure | Description |
27!> |-----------|-------------|
28!> | vtable_add | Add entry to variable table |
29!> | vtable_delete | Delete entry from variable table |
30!> | vtable_lookup | Look up entry in variable table |
31!> | vtable_set_attrid | Set attribute iterator ID |
32!>
33!> @enden
34!>
35!> @ja
36!> @brief gtdata_netcdf 内で使用される内部向け定数, 変数, 手続き群
37!>
38!> このモジュールは内部変数テーブル (gdnctab) とその管理手続きを提供します。
39!>
40!> | 手続き | 説明 |
41!> |--------|------|
42!> | vtable_add | 変数テーブルにエントリを追加 |
43!> | vtable_delete | 変数テーブルからエントリを削除 |
44!> | vtable_lookup | 変数テーブルでエントリを検索 |
45!> | vtable_set_attrid | 属性イテレータ ID を設定 |
46!>
47!> @endja
48!>
50 !
51
52 use netcdf
53 use gtdata_netcdf_types, only: &
55 use dc_error
56 use dc_trace, only: dbgmessage
57 implicit none
58 private
59
60 type(GD_NC_VARIABLE_ENTRY), save, target, allocatable:: gdnctab(:)
61 integer, parameter:: gdnctab_init_size = 16
62
64 public:: vtable_set_attrid
65
66contains
67
68 !>
69 !> @en
70 !> @brief Add entry to variable table
71 !>
72 !> Adds a new entry to gdnctab or returns existing entry if already registered.
73 !> @enden
74 !>
75 !> @ja
76 !> @brief 変数テーブルにエントリを追加
77 !>
78 !> gdnctab に新しいエントリを追加、または既登録なら既存エントリを返します。
79 !> @endja
80 !>
81 !> @param[out] var @en Variable handle @enden @ja 変数ハンドル @endja
82 !> @param[in] entry @en Entry to add @enden @ja 追加するエントリ @endja
83 !> @return @en NF90_NOERR on success, NF90_ENOMEM on allocation failure @enden
84 !> @ja 成功時 NF90_NOERR、割当失敗時 NF90_ENOMEM @endja
85 !>
86 integer function vtable_add(var, entry) result(result)
87 type(gd_nc_variable), intent(out):: var
88 type(gd_nc_variable_search), intent(in):: entry
89 type(gd_nc_variable_entry), allocatable:: tmp_table(:)
90 integer:: i, n
91
92 ! --- 必要なら初期確保 ---
93 if (.not. allocated(gdnctab)) then
94 allocate(gdnctab(gdnctab_init_size), stat=result)
95 if (result /= 0) goto 999
96 do, i = 1, gdnctab_init_size
97 gdnctab(i)%fileid = 0
98 gdnctab(i)%varid = 0
99 gdnctab(i)%dimid = 0
100 gdnctab(i)%attrid = 0
101 nullify(gdnctab(i)%dimids)
102 enddo
103 endif
104 ! --- 同じ内容が既登録ならばそれを返す (attrid は変更しない) ---
105 do, i = 1, size(gdnctab)
106 if (gdnctab(i)%fileid == entry%fileid &
107 & .and. gdnctab(i)%varid == entry%varid &
108 & .and. gdnctab(i)%dimid == entry%dimid) then
109 var = gd_nc_variable(i)
110 result = nf90_noerr
111 call dbgmessage('gtdata_netcdf_internal.add: found %d', i=(/i/))
112 return
113 endif
114 enddo
115 !
116 ! --- 空き地があればそこに割り当て ---
117 var = gd_nc_variable(-1)
118 do, i = 1, size(gdnctab)
119 if (gdnctab(i)%fileid == 0) then
120 var = gd_nc_variable(i)
121 exit
122 endif
123 enddo
124 if (var%id == -1) then
125 ! --- 空き地はなかったのだから倍幅確保 ---
126 n = size(gdnctab)
127 allocate(tmp_table(n), stat=result)
128 if (result /= 0) goto 999
129 tmp_table(:) = gdnctab(:)
130 deallocate(gdnctab, stat=result)
131 if (result /= 0) goto 999
132 allocate(gdnctab(n * 2), stat=result)
133 if (result /= 0) goto 999
134 gdnctab(1:n) = tmp_table(1:n)
135 deallocate(tmp_table, stat=result)
136 if (result /= 0) goto 999
137 !
138 gdnctab(n+2)%fileid = 0
139 gdnctab(n+2)%varid = 0
140 gdnctab(n+2)%dimid = 0
141 gdnctab(n+2)%attrid = 0
142 nullify(gdnctab(n+2)%dimids)
143 gdnctab(n+3: n*2) = gdnctab(n+2)
144 ! 確保域の先頭を使用
145 var = gd_nc_variable(n + 1)
146 endif
147 gdnctab(var%id)%fileid = entry%fileid
148 gdnctab(var%id)%varid = entry%varid
149 gdnctab(var%id)%dimid = entry%dimid
150 !
151 ! --- 次元表の確保 ---
152 call internal_build_dimids(gdnctab(var%id), result)
153 if (result /= nf90_noerr) goto 999
154 !
155 result = nf90_noerr
156 call dbgmessage('gtdata_netcdf_internal.add: added %d', i=(/var%id/))
157 return
158 !
159999 continue
160 var = gd_nc_variable(-1)
161 result = nf90_enomem
162 return
163
164 contains
165
166 subroutine internal_build_dimids(ent, stat)
167!! use netcdf, only: &
168!! & NF90_NOERR, NF90_ENOMEM, NF90_INQUIRE_VARIABLE
169 type(gd_nc_variable_entry), intent(inout):: ent
170 integer, intent(out):: stat
171 integer:: ndims
172 if (ent%varid > 0) then
173 stat = nf90_inquire_variable(ent%fileid, ent%varid, ndims = ndims)
174 if (stat /= nf90_noerr) return
175 if ((ent%dimid > 0) .and. (ndims /= 1)) goto 100
176 if (ndims == 0) then
177 nullify(ent%dimids)
178 stat = nf90_noerr
179 return
180 endif
181 allocate(ent%dimids(ndims), stat=stat)
182 if (stat /= 0) then
183 stat = nf90_enomem
184 return
185 endif
186 stat = nf90_inquire_variable(ent%fileid, ent%varid, dimids = ent%dimids)
187 if (stat /= nf90_noerr) return
188 if ((ent%dimid > 0) .and. (ent%dimids(1) /= ent%dimid)) then
189 deallocate(ent%dimids)
190 goto 100
191 endif
192 else
193 allocate(ent%dimids(1), stat=stat)
194 if (stat /= 0) then
195 stat = nf90_enomem
196 return
197 endif
198 ent%dimids(1) = ent%dimid
199 endif
200 stat = nf90_noerr
201 return
202
203100 continue
204 ent%varid = 0
205 allocate(ent%dimids(1))
206 ent%dimids(1) = ent%dimid
207 end subroutine internal_build_dimids
208
209 end function vtable_add
210
211 !>
212 !> @en
213 !> @brief Delete entry from variable table
214 !>
215 !> Returns fileid on success, NF90_ENOTVAR on failure.
216 !> @enden
217 !>
218 !> @ja
219 !> @brief 変数テーブルからエントリを削除
220 !>
221 !> 成功時は fileid を、失敗時は NF90_ENOTVAR を返します。
222 !> @endja
223 !>
224 !> @param[in] var @en Variable handle @enden @ja 変数ハンドル @endja
225 !> @return @en fileid on success, NF90_ENOTVAR on failure @enden
226 !> @ja 成功時 fileid、失敗時 NF90_ENOTVAR @endja
227 !>
228 integer function vtable_delete(var) result(result)
229 type(gd_nc_variable), intent(in):: var
230 if (.not. allocated(gdnctab)) goto 999
231 if (var%id <= 0 .or. var%id > size(gdnctab)) goto 999
232 if (gdnctab(var%id)%fileid == 0) goto 999
233 result = gdnctab(var%id)%fileid
234 gdnctab(var%id)%fileid = 0
235 gdnctab(var%id)%varid = 0
236 gdnctab(var%id)%dimid = 0
237 gdnctab(var%id)%attrid = 0
238 if (associated(gdnctab(var%id)%dimids)) &
239 & deallocate(gdnctab(var%id)%dimids)
240 call dbgmessage('gtdata_netcdf_internal.delete: delete %d', i=(/var%id/))
241 return
242 !
243999 continue
244 result = nf90_enotvar
245 end function vtable_delete
246
247 !>
248 !> @en
249 !> @brief Look up entry in variable table
250 !> @enden
251 !> @ja
252 !> @brief 変数テーブルでエントリを検索
253 !> @endja
254 !>
255 !> @param[in] var @en Variable handle @enden @ja 変数ハンドル @endja
256 !> @param[out] entry @en Found entry @enden @ja 見つかったエントリ @endja
257 !> @return @en NF90_NOERR on success, NF90_ENOTVAR if not found @enden
258 !> @ja 成功時 NF90_NOERR、未発見時 NF90_ENOTVAR @endja
259 !>
260 integer function vtable_lookup(var, entry) result(result)
261 type(gd_nc_variable), intent(in):: var
262 type(gd_nc_variable_entry), intent(out):: entry
263 if (.not. allocated(gdnctab)) goto 999
264 if (var%id <= 0 .or. var%id > size(gdnctab)) goto 999
265 if (gdnctab(var%id)%fileid == 0) goto 999
266 entry = gdnctab(var%id)
267 result = nf90_noerr
268 return
269 !
270999 continue
271 nullify(entry%dimids)
272 entry%fileid = -1
273 entry%varid = -1
274 entry%dimid = -1
275 entry%attrid = -1
276 result = nf90_enotvar
277 end function vtable_lookup
278
279 !>
280 !> @en
281 !> @brief Set attribute iterator ID for a variable
282 !> @enden
283 !> @ja
284 !> @brief 変数の属性イテレータ ID を設定
285 !> @endja
286 !>
287 !> @param[in] var @en Variable handle @enden @ja 変数ハンドル @endja
288 !> @param[in] attrid @en Attribute iterator ID @enden @ja 属性イテレータ ID @endja
289 !> @return @en NF90_NOERR on success, NF90_ENOTVAR on failure @enden
290 !> @ja 成功時 NF90_NOERR、失敗時 NF90_ENOTVAR @endja
291 !>
292 integer function vtable_set_attrid(var, attrid) result(result)
293 type(gd_nc_variable), intent(in):: var
294 integer, intent(in):: attrid
295 continue
296 if (.not. allocated(gdnctab)) goto 999
297 if (var%id <= 0 .or. var%id > size(gdnctab)) goto 999
298 if (gdnctab(var%id)%fileid == 0) goto 999
299 gdnctab(var%id)%attrid = attrid
300 result = nf90_noerr
301 return
302 !
303999 continue
304 result = nf90_enotvar
305 end function vtable_set_attrid
306
307end module gtdata_netcdf_internal
エラー処理用モジュール
Definition dc_error.f90:454
デバッグ時の追跡用モジュール
Definition dc_trace.f90:150
subroutine, public dbgmessage(fmt, i, r, d, l, n, c1, c2, c3, ca)
Definition dc_trace.f90:661
integer function, public vtable_delete(var)
integer function, public vtable_set_attrid(var, attrid)
integer function, public vtable_add(var, entry)
integer function, public vtable_lookup(var, entry)