...
Info |
---|
|
"You’re a man looking at the world through a keyhole, and you’ve spent your whole life trying to widen that keyhole, to see more, to know more, and now, on hearing that it can be widened, in ways you can’t imagine you reject the possibility." The Ancient One - Doctor Strange |
Table of Contentschildren |
---|
Info |
---|
code parameters allow to store varaibles and parameters outside of actor code in elegant way. The IMAS environment has specially dedicated Fortran library - xmllib XMLLIB to handle it. |
Image Removed
Accessing code parameters from pure IMAS code
Prepare your environment:
Code Block |
---|
$ module load imasenv/3.24.0/rc
$ mkdir -p $ITMWORK/projects
$ cd $ITMWORK/projects
$ cp -r $SWIMASDIR/resources/tutorials/2019-10-PSNC/code_parameters . |
Info |
---|
Before proceeding any further, make sure you have configured your Kepler environment. Take a look here 00. Initial setup or here 05.3. IMAS - basic topics - environment set-up(POZ'19Oct) |
The structure of your working directory should look like this:
Code Block |
---|
$ cd code_parameters
$ tree
.
├── input_test_xmllib_pathquery.xml
├── input_test_xmllib_pathquery.xsd
├── Makefile # instructions on how to compile
├── sample_default.xml
├── sample.f90 # code with accessing code parameters
├── sample.xml # file with parameters
└── sample.xsd # defining the structure of an XML document |
A sample xml file containing information in the form of parameters for an actor:
Code Block |
---|
|
<?xml version="1.0"?>
<?xml-stylesheet type="text/xsl" href="./ets.xsl" charset="ISO-8859-1"?>
<parameters>
<input>
<shot_in> 4 </shot_in> <!-- shot number -->
<run_in> 1 </run_in> <!-- run number -->
<interpol> 1 </interpol> <!-- interpolation index -->
<time_dep_input> 0 </time_dep_input> <!-- 1 implies time dependence in input data -->
</input>
<output>
<shot_out> 5 </shot_out> <!-- shot number -->
<run_out> 2 </run_out> <!-- run number -->
<tau_out> 0.0003 </tau_out> <!-- output frequency -->
<db_out> mdsplus </db_out> <!-- output database format -->
</output>
<dims>
<nrho> 50 </nrho> <!-- NRHO, number of radial points -->
<npsi> 100 </npsi> <!-- NPSI, number of equilibrium points -->
<neq_dim1> 100 </neq_dim1> <!-- NDIM1, number of points for 2-D equilibrium signals in R direction -->
<neq_dim2> 100 </neq_dim2> <!-- NDIM2, number of points for 2-D equilibrium signals in Z direction -->
<neq_max_npoints> 100 </neq_max_npoints> <!-- MAX_NPOINTS, number of equilibrium boundary points -->
</dims>
...
<experimental>
<option> -1 </option> <!-- option #: 0: disabled -->
</experimental>
</parameters> |
The first 35 lines of this code show how you can handle reading of the xml file in which the actor's parameters are saved:
Code Block |
---|
title | sample.f90 |
---|
linenumbers | true |
---|
|
!> Test program Christian Konz version of xmllib.
program sample
use xml_file_reader, only: fill_param
use xml2eg_mdl
use xmllib_parser, only: element, tree, xmllib_parse, destroy_xml_tree
use string_manipulation_tools
implicit none
! Input parameters, read from file
character(132), pointer :: param_xml(:) => NULL()
character(132), pointer :: param_xsd(:) => NULL()
character(132), pointer :: param_default(:) => NULL()
! Input file names:
character(132) :: fn_xml = 'sample.xml'
character(132) :: fn_xml_default = 'sample.xml'
character(132) :: fn_xsd = 'sample.xsd'
! Representation of xml parameters
TYPE(tree) :: parameter_list
TYPE(element), POINTER :: temp_pointer => null()
character(len = 132) :: cname
! Values parser from xml
integer :: shot_in, run_in
integer(4) :: nparm
real(8) :: geo_ax
call fill_param(param_xml, param_default, param_xsd, fn_xml, fn_xml_default, fn_xsd)
CALL XMLLIB_PARSE(param_xml, param_xsd, param_default, nparm, parameter_list)
temp_pointer => parameter_list%first
outer: do
write(*,*)'Next xml element: ',temp_pointer%cname
cname = char2str(temp_pointer%cname) ! necessary for AIX
!write(0,*)'RFOF_input::RFOF_parse_xml_input_param, cname=',trim(cname)
select case (cname)
...
end select
do
if (associated(temp_pointer%sibling)) then
temp_pointer => temp_pointer%sibling
exit
end if
if (associated(temp_pointer%parent, parameter_list%first )) &
exit outer
if (associated(temp_pointer%parent)) then
temp_pointer => temp_pointer%parent
else
write(0, *) 'ERROR: broken list.'
stop
end if
end do
end do outer
!-- destroy tree
call destroy_xml_tree(parameter_list)
end program sample
|
Run an example:
Code Block |
---|
$ module load imasenv/3.24.0/rc # load environment if not set
$ make
ifort -fPIC -g -I/gw/swimas/extra/xmllib/3.2.0/intel/17.0/include/xmllib -I/usr/include/libxml2 -c -o sample.o sample.f90
ifort -fPIC -g -o sample.exe sample.o -L/gw/swimas/extra/xmllib/3.2.0/intel/17.0/lib -lxmllib -lxml2
./sample.exe
Next xml element: parameters
Next xml element: input
Next xml element: shot_in
Read shot_in= 4
Next xml element: run_in
Read shot_in= 1
Next xml element: interpol
Next xml element: time_dep_input
Next xml element: output
Next xml element: dims
Next xml element: compositions
Next xml element: startup
Next xml element: boundary
Next xml element: equilibrium
Next xml element: geo_ax
Read geo_ax= 2.86000000000000
Next xml element: plasma_ax
Next xml element: amin
Next xml element: elong
Next xml element: tria_up
Next xml element: tria_low
Next xml element: solver
Next xml element: experimental |
Compare result with data inside sample.xml file.
Accessing code parameters from FC2K actor
Info |
---|
Before proceeding any further, make sure you have configured your Kepler environment. Take a look here 00. Initial setup or here 05.3. IMAS - basic topics - environment set-up(POZ'19Oct) |
Prepare your environment:
Code Block |
---|
$ module load imasenv/3.24.0/rc
$ mkdir -p $ITMWORK/projects
$ cd $ITMWORK/projects
$ git clone ssh://git@git.iter.org/imex/fc2k-testing-framework.git
# OR copy from this location
$ cp -r $SWIMASDIR/resources/tutorials/2019-10-PSNC/fc2k-testing-framework . |
The structure of your working directory should look like this:
Code Block |
---|
$ cd fc2k-testing-framework/primitives_param/fortran/
$ tree
.
├── clean.sh
├── Makefile
├── primitives_param.f90 # FC2K actor with accessing code parameters
├── primitivesparam_fc2k.xml # FC2K configuration file
├── primitivesparam_workflow.xml # example workflow
├── run_test.sh # script for run example
├── sample_default.xml
├── sample.xml # XML file with parameters
└── sample.xsd # defining the structure of an XML document |
Let's see what the xml file looks like with the parameters.
Suppose we want to download an "i" parameter from this file.
Code Block |
---|
|
<?xml version="1.0"?>
<parameters>
<r> 3.141592 </r>
<i> 2 </i>
<boolean> True False </boolean>
<realVec> 2.7e2 4.0 </realVec>
<intVec> 13 7 </intVec>
<booleanVec> True False </booleanVec>
</parameters> |
Below is an example of the code that retrieves parameters/i value from an xml file:
Code Block |
---|
title | primitives_param.f90 |
---|
linenumbers | true |
---|
|
subroutine primitivesparam(in_input, out_output, user_in_codeparamstruct)
use ids_schemas, only: ids_real, ids_int, ids_equilibrium, ids_core_profiles, ids_parameters_input
use xml2eg_mdl, only: xml2eg_parse_memory, xml2eg_get, type_xml2eg_document, xml2eg_free_doc, set_verbose
use iso_c_binding, only: c_int
implicit none
integer, intent(in) :: in_input
integer, intent(out) :: out_output
integer(ids_int) :: value_int
integer(c_int) :: tmp_value_int
type(ids_parameters_input) :: user_in_codeparamstruct
type(type_xml2eg_document) :: doc
! Parse the "codeparam_string". This means that the data is put into a document "doc"
call xml2eg_parse_memory( user_in_codeparamstruct%parameters_value, doc )
call set_verbose(.TRUE.)
! Extract data in "doc" at position "parameters/i" and store it in "int_value"
call xml2eg_get( doc , 'i' , tmp_value_int)
value_int = int( tmp_value_int, ids_int )
! Make sure to clean up after you!!
! When calling "xml2eg_parse_memory" memory was allocated in the "doc" object.
! This memory is freed by "xml2eg_free_doc(doc)"
call xml2eg_free_doc(doc)
out_output = in_input + value_int
return
end subroutine |
Run an example:
Code Block |
---|
$ module load imasenv/3.24.0/rc # load environment if not set
$ ./run_test.sh
Compilation - OK
Skipping log removal
FC2K build for primitives with params - OK
Skipping log removal
Workflow execution: primitives with params - OK
Skipping log removal
Checking output - should be equal to '3' - OK
Skipping log removal |
...
XMLLIB library basics
The main idea of the library
Image Added
Short description of XMLLIB API - main points
Code Block |
---|
xml2eg_parse_memory(character(len=*) parameters , type(type_xml2eg_document) xml2eg_document) |
This function allows you to read to memory the entire xml file containing the list of parameters.
Parse the "codeparam_string". This means that the data is put into a xml2eg_document.
Code Block |
---|
xml2eg_get(type(type_xml2eg_document) xml2eg_document, character(len=*) path, <any type> output_value) |
The function allows reading the parameter that is in the path location inside xml file.
Data is extracted from the xml2eg_document file is the output_value variable.
Code Block |
---|
xml2eg_free_doc(type(type_xml2eg_document) xml2eg_document) |
Cleaning and freeing allocated memory of xml2eg_document object.
Tip |
---|
A more detailed description of the XMLLIB library can be found here. |