wxios.F90

源码路径:

LMDZ.COMMON-6.3\LMDZ.COMMON\libf\misc\wxios.F90

Mars 运行参与度:条件经过。CPP_XIOS 构建中,COMMON gcm/并行初始化会调用 wxios_init,Mars physiq_mod 会调用 wxios_context_init,Mars xios_output_mod 通过 wxios_domain_paramwxios_domain_param_unstructured 初始化 horizontal domain,并用 wxios_closedef 关闭 context definition。未启用 CPP_XIOS 时,本文件主体不提供 wxios 模块能力。

文件职责

wxios 是 COMMON 对 XIOS v2 的薄封装,负责:

它不定义 Mars physics 变量清单。Mars 变量、axis 语义和实际发送由 Mars xios_output_mod.F90 与 XML 文件控制;wxios 只提供 context/domain/file/field 操作工具。

编译边界和版本约束

整个文件位于:

#ifdef CPP_XIOS
MODULE wxios
...
END MODULE wxios
#endif

文件还显式拒绝 XIOS v1:

#ifdef XIOS1
#error "XIOS v1 no longer supported, use XIOS v2."
#endif

因此依赖本模块的调用点必须处在 XIOS 构建条件中,或由构建系统保证 CPP_XIOS 已启用。

模块状态

状态 类型 并行属性 含义
g_comm integer save THREADPRIVATE 指令中列出 xios_initialize 返回的 communicator。
g_ctx_name character save, default "LMDZ" 见待确认 默认 context name,wxios_init 写入,wxios_context_init/wxios_set_context 读取。
g_ctx xios_context save THREADPRIVATE 指令中列出 保存 xios_get_handle(g_ctx_name,...) 得到的 context handle。
g_flag_xml logical save THREADPRIVATE 最近一次 field 是否由 XML 预定义。
g_field_name character, default "nofield" THREADPRIVATE 最近一次处理的 field 名,避免重复创建。
missing_val_omp, missing_val real missing_valTHREADPRIVATE 当前文件内未见实质使用。

源码 OpenMP 指令写为 THREADPRIVATE(g_comm,g_cts_name,g_ctx),其中 g_cts_name 与声明的 g_ctx_name 不一致。页面按源码事实记录:g_ctx_name 是否真正 threadprivate 需要编译器/OpenMP 诊断或运行验证确认。

例程清单

例程 行为
reformadate(odate, ndate) 36day1hr1mth 这类 IOIPSL 风格片段写入 xios_duration 的 day/hour/month。
reformaop(op) inst(X)oncet_max(X)t_min(X) 映射到 XIOS instant/once/maximum/minimum;其他默认 average
wxios_init(xios_ctx_name, locom, outcom, type_ocean) 调用 xios_initialize,可传 local communicator,可返回 XIOS communicator,并保存 g_comm/g_ctx_name
wxios_context_init() COMM_LMDZ_PHY 上初始化 g_ctx_name context,设为 current context,并调用 xios_solve_inheritance
wxios_set_context() 重新获取并激活 g_ctx_name context。
wxios_set_cal(...) 根据 earth_360d/earth_365d/gregorian 设置 calendar、origin/start date 和 timestep;其他 calendar abort。
wxios_set_timestep(ts) mdtime%timestep=ts 形式设置 XIOS timestep。
wxios_domain_param(dom_id, flip_coordinates) 为 regular lon-lat domain 写入 ni_glo/nj_glo、local j-slice、lon/lat 1D 值和 MPI overlap mask。
wxios_domain_param_unstructured(dom_id, flip_coordinates) 为 unstructured domaingroup 写入 lon/lat、cell bounds、i_indexnvertex
wxios_add_vaxis(axis_id, axis_size, axis_value) 设置 XIOS axis n_glo/value,并检查 axis 是否有效。
wxios_add_file(fname, ffreq, flvl) 如果 XML 中没有该 file,则在 defile 下添加 file fname,输出名为 "X"//fname,并设置频率和 level;若 XML 已定义则只启用。
wxios_add_field(fieldname, fieldgroup, fieldlongname, fieldunit) 向 field group 添加 field,设置 standard name、unit 和 default fill value。
wxios_add_field_to_file(...) 按 2D/3D 选择 field group,创建或启用 field,把 field 加到 file,并设置 operation、freq_op、level、axis。
wxios_closedef() 调用 xios_close_context_definition()
wxios_close() 依次调用 xios_context_finalize()xios_finalize()

初始化和关闭链

COMMON GCM/XIOS 初始化

dyn3d/gcm.F90
  -> wxios_init("LMDZ")

dyn3dpar/mod_const_mpi.F90
  -> wxios_init("LMDZ", outcom=COMM_LMDZ, type_ocean=...)
  -> wxios_init("LMDZ", outcom=COMM_LMDZ)
  -> wxios_init("LMDZ")

wxios_init 只调用 xios_initialize 并保存 context name/communicator;源码中 wxios_context_init 的调用被注释掉,context 初始化由后续 physics/Mars 路径触发。

Mars physics context 和 domain

Mars physiq_mod
  -> wxios_context_init

Mars xios_output_mod:initialize_xios_output
  -> xios_set_axis_attr("presnivs"/"altitude"/"interlayer"/"soil_layers"/"subslope")
  -> if grid_type==unstructured:
         wxios_domain_param_unstructured("dom_glo")
     else:
         wxios_domain_param("dom_glo")
  -> xios_define_calendar(...)
  -> xios_set_time_origin(...)
  -> xios_set_start_date(...)
  -> wxios_closedef()

Mars xios_output_mod 直接定义垂直 axis 和 Mars calendar;wxios 在这条链中主要负责 horizontal domain 与 context definition close。

关闭路径

dyn3d/abort_gcm.F
  -> wxios_close()

dyn3dpar/parallel_lmdz.F90
  -> wxios_close()

Mars xios_output_mod:finalize_xios_output 也会调用 XIOS context finalize,但不经 wxios_close

regular lon-lat domain

wxios_domain_param(dom_id, flip_coordinates)geometry_mod 收集当前 physics grid 的角度制经纬度:

  1. 可选 flip_coordinates 时对 latitude_deg/longitude_deg 取负。
  2. 调用物理 transfer gatherrlat_glo/rlon_glo,再 bcast 给所有 rank。
  3. OMP MASTER 从全局物理列数组构造 regular 轴:
    • io_lat(1)=rlat_glo(1)
    • io_lat(nbp_lat)=rlat_glo(klon_glo)
    • 中间纬度取 rlat_glo(2+(i-2)*nbp_lon)
    • klon_glo==1io_lon(1)=rlon_glo(1);否则 io_lon(1:nbp_lon)=rlon_glo(2:nbp_lon+1)
  4. 设置 XIOS domain:
    • ni_glo=nbp_lon, ibegin=0, ni=nbp_lon, type="rectilinear"
    • nj_glo=nbp_lat, jbegin=jj_begin-1, nj=jj_nb, data_dim=2
    • lonvalue_1d=io_lon, latvalue_1d=io_lat(jj_begin:jj_end)
  5. 非 sequential 模式下构造 mask(nbp_lon,jj_nb),屏蔽 MPI overlap,南极特殊 rank 可重新打开最后一行。

这个 domain 是当前 MPI rank 的纬向块,和 mod_grid_phy_lmdznbp_lon/nbp_lat/klon_glo 约定一致。

unstructured domain

wxios_domain_param_unstructured(dom_id, flip_coordinates) 直接使用 geometry_mod 的局部几何状态:

输入状态 转换 用途
longitude, latitude *180/PI,可选取负 cell center lon/lat。
boundslon, boundslat *180/PI,可选取负,传入前 TRANSPOSE cell vertex bounds。
ind_cell_glo gather_omp 后减 1 XIOS i_index,Fortran 1-based 转 XIOS 0-based。
nvertex, klon_glo 直接使用 XIOS nvertex 和 global cell count。
ij_begin, ij_nb, klon_mpi 物理并行状态 当前 rank unstructured slice。

该例程设置 domaingroup 属性:ni_glo=klon_gloibegin=ij_begin-1ni=ij_nbtype="unstructured",并写入 bounds 与 cell index。

file/field 动态定义

wxios_add_filewxios_add_field_to_file 是旧 IOIPSL/XIOS 桥接风格的动态定义 helper:

Mars 当前 xios_output_mod 主要使用 XML 和 xios_set_axis_attr/xios_send_field 路径;这些动态 file/field helper 是 COMMON 通用 XIOS 桥接能力。

与 xios_writefield 的关系

xios_writefield 使用本模块的三个例程:

xios_writefield 调用 wxios 提供的能力
wxios_domain_param("domain") regular lon-lat domain 属性。
wxios_domain_param_unstructured("domaingroup") unstructured domaingroup 属性。
wxios_set_context() 临时 context_lmdz_<field> 发送结束后恢复默认 LMDZ context。

二者分工不同:xios_writefield 是按字段名创建临时 context/file/field 的 dump helper;wxios 是更底层的 context、domain、axis、file 和 field 操作封装。

复现要点

  1. 必须启用 CPP_XIOS,且不能使用 XIOS1
  2. wxios_init 之后还需要 wxios_context_init 才会在 COMM_LMDZ_PHY 上创建并激活 context。
  3. Mars physics 输出 domain id 是 "dom_glo";临时 xios_writefield 使用 "domain""domaingroup"
  4. regular domain 的 lon/lat 来自 geometry_mod 的角度制局部数组 gather 后重构,不直接读取 regular_lonlat_mod:lon_reg/lat_reg
  5. unstructured domain 的 bounds 使用弧度几何状态乘 180/PI,并把 ind_cell_glo 转成 0-based i_index
  6. wxios_set_cal 只接受 earth_360dearth_365dgregorian;Mars xios_output_mod 自己定义 user-defined calendar。
  7. 动态 file 输出名会加 X 前缀,即 fname 对应 "X"//fname

待确认

相关页面