46#include "../base/base_uses.f90"
51 LOGICAL,
PRIVATE,
PARAMETER :: debug_this_module = .true.
52 CHARACTER(len=*),
PARAMETER,
PRIVATE :: moduleN =
'input_parsing'
70 LOGICAL,
INTENT(in),
OPTIONAL :: root_section
72 CHARACTER(len=*),
PARAMETER :: routinen =
'section_vals_parse'
74 CHARACTER(len=max_line_length) :: token
75 INTEGER :: desc_level, handle, ik, imatch, irs, is, &
77 LOGICAL :: at_end, compatible_end, root_sect, &
85 CALL timeset(routinen, handle)
87 NULLIFY (previous_list, previous_last)
90 IF (
PRESENT(root_section)) root_sect = root_section
92 cpassert(
ASSOCIATED(section_vals))
95 cpassert(section_vals%ref_count > 0)
96 IF (root_sect .AND. parser%icol1 > parser%icol2) &
97 CALL cp_abort(__location__, &
98 "Error 1: this routine must be called just after having parsed the start of the section " &
100 section => section_vals%section
102 token = trim(adjustl(parser%input_line(parser%icol1:parser%icol2)))
104 IF (token /= parser%section_character//section%name) &
105 CALL cp_abort(__location__, &
106 "Error 2: this routine must be called just after having parsed the start of the section " &
109 IF (.NOT. section%repeats .AND.
SIZE(section_vals%values, 2) /= 0) &
110 CALL cp_abort(__location__,
"Section "//trim(section%name)// &
113 irs =
SIZE(section_vals%values, 2)
115 IF (
ASSOCIATED(section%keywords(-1)%keyword))
THEN
116 keyword => section%keywords(-1)%keyword
119 CALL val_create_parsing(el, type_of_var=keyword%type_of_var, &
120 n_var=keyword%n_var, default_value=keyword%lone_keyword_value, &
121 enum=keyword%enum, unit=keyword%unit, &
122 default_units=default_units, &
126 section_vals%values(-1, irs)%list => new_val
131 lower_to_upper=.true., at_end=at_end)
132 token = trim(adjustl(token))
135 CALL cp_abort(__location__, &
136 "unexpected end of file while parsing section "// &
140 IF (token(1:1) == parser%section_character)
THEN
141 IF (token ==
"&END")
THEN
143 compatible_end = .true.
146 lower_to_upper=.true.)
147 IF (token /=
"SECTION" .AND. token /= section%name)
THEN
148 compatible_end = .false.
153 lower_to_upper=.true.)
154 IF (token /= section%name)
THEN
155 print *, trim(token),
"/=", trim(section%name)
156 compatible_end = .false.
159 IF (.NOT. compatible_end)
THEN
160 CALL cp_abort(__location__, &
161 "non-compatible end of section "//trim(section%name)//
" "// &
170 default_units=default_units, parser=parser)
173 IF (output_unit > 0)
THEN
174 WRITE (output_unit, *)
175 WRITE (output_unit,
'(T2,A)')
"Possible matches for unknown subsection "
176 WRITE (output_unit, *)
177 WRITE (output_unit,
'(T2,A)') trim(token(2:))
178 WRITE (output_unit, *)
185 CALL cp_abort(__location__, &
186 "unknown subsection "//trim(token(2:))//
" of section " &
187 //trim(section%name))
191 lower_to_upper=.true.)
192 IF (token(1:1) == parser%section_character)
THEN
193 IF (token ==
"&END")
THEN
202 IF (token ==
"DESCRIBE")
THEN
203 IF (output_unit > 0)
WRITE (output_unit,
"(/,' ****** DESCRIPTION ******',/)")
208 whole_section = .true.
210 whole_section = .false.
212 lower_to_upper=.true.)
214 IF (.NOT.
ASSOCIATED(keyword))
THEN
215 CALL cp_warn(__location__, &
216 "unknown keyword to describe "//trim(token)// &
217 " in section "//trim(section%name))
222 IF (whole_section)
THEN
223 CALL section_describe(section, output_unit, desc_level, hide_root=.NOT. root_sect)
225 IF (output_unit > 0)
WRITE (output_unit,
"(/,' ****** =========== ******',/)")
230 parser%icol = parser%icol1 - 1
232 IF (.NOT.
ASSOCIATED(section%keywords(0)%keyword))
THEN
233 IF (output_unit > 0)
THEN
234 WRITE (output_unit, *)
235 WRITE (output_unit,
'(T2,A)')
"Possible matches for unknown keyword "
236 WRITE (output_unit, *)
237 WRITE (output_unit,
'(T2,A)') trim(token)
238 WRITE (output_unit, *)
242 WRITE (output_unit,
'(T2,A,1X,I0)') &
246 CALL cp_abort(__location__, &
247 "found an unknown keyword "//trim(token)// &
248 " in section "//trim(section%name))
251 keyword => section%keywords(ik)%keyword
252 IF (
ASSOCIATED(keyword))
THEN
253 IF (keyword%removed)
THEN
254 IF (
ALLOCATED(keyword%deprecation_notice))
THEN
255 CALL cp_abort(__location__, &
256 "The specified keyword '"//trim(token)//
"' is not available anymore: "// &
257 keyword%deprecation_notice)
259 CALL cp_abort(__location__, &
260 "The specified keyword '"//trim(token)// &
261 "' is not available anymore, please consult the manual.")
265 IF (
ALLOCATED(keyword%deprecation_notice)) &
266 CALL cp_warn(__location__, &
267 "The specified keyword '"//trim(token)// &
268 "' is deprecated and may be removed in a future version: "// &
269 keyword%deprecation_notice//
".")
272 IF (ik /= 0 .AND. keyword%type_of_var ==
lchar_t) &
274 CALL val_create_parsing(el, type_of_var=keyword%type_of_var, &
275 n_var=keyword%n_var, default_value=keyword%lone_keyword_value, &
276 enum=keyword%enum, unit=keyword%unit, &
277 default_units=default_units, parser=parser)
278 IF (
ASSOCIATED(el))
THEN
281 last_val => section_vals%values(ik, irs)%list
282 IF (.NOT.
ASSOCIATED(last_val))
THEN
283 section_vals%values(ik, irs)%list => new_val
285 IF (.NOT. keyword%repeats) &
286 CALL cp_abort(__location__, &
287 "Keyword "//trim(token)// &
288 " in section "//trim(section%name)//
" should not repeat.")
289 IF (
ASSOCIATED(last_val, previous_list))
THEN
290 last_val => previous_last
292 previous_list => last_val
294 DO WHILE (
ASSOCIATED(last_val%rest))
295 last_val => last_val%rest
297 last_val%rest => new_val
298 previous_last => new_val
305 CALL timestop(handle)
322 SUBROUTINE val_create_parsing(val, type_of_var, n_var, enum, &
323 parser, unit, default_units, default_value)
325 INTEGER,
INTENT(in) :: type_of_var, n_var
330 TYPE(
val_type),
OPTIONAL,
POINTER :: default_value
332 CHARACTER(len=*),
PARAMETER :: routinen =
'val_create_parsing'
334 CHARACTER(len=default_string_length) :: c_val, info, location
335 CHARACTER(len=default_string_length), &
336 DIMENSION(:),
POINTER :: c_val_p
337 INTEGER :: handle, i, i_val
338 INTEGER,
DIMENSION(:),
POINTER :: i_val_p
339 LOGICAL :: check, eol, l_val, quoted
340 LOGICAL,
DIMENSION(:),
POINTER :: l_val_p
341 REAL(kind=
dp) :: r_val
342 REAL(kind=
dp),
DIMENSION(:),
POINTER :: r_val_p
348 CALL timeset(routinen, handle)
350 cpassert(.NOT.
ASSOCIATED(val))
351 SELECT CASE (type_of_var)
356 IF (.NOT.
ASSOCIATED(default_value))
THEN
358 ALLOCATE (l_val_p(0))
361 CALL cp_abort(__location__, &
362 "no value was given and there is no default value"// &
366 cpassert(
ASSOCIATED(default_value%l_val))
367 CALL val_create(val, l_vals=default_value%l_val)
371 NULLIFY (l_last, l_first)
384 ALLOCATE (l_val_p(n_var))
389 IF (
ASSOCIATED(l_val_p))
THEN
396 IF (.NOT.
ASSOCIATED(default_value))
THEN
398 ALLOCATE (i_val_p(0))
401 CALL cp_abort(__location__, &
402 "no value was given and there is no default value"// &
406 check =
ASSOCIATED(default_value%i_val)
408 CALL val_create(val, i_vals=default_value%i_val)
412 NULLIFY (i_last, i_first)
425 ALLOCATE (i_val_p(n_var))
430 IF (
ASSOCIATED(i_val_p))
THEN
437 IF (.NOT.
ASSOCIATED(default_value))
THEN
439 ALLOCATE (r_val_p(0))
442 CALL cp_abort(__location__, &
443 "no value was given and there is no default value"// &
447 cpassert(
ASSOCIATED(default_value%r_val))
448 CALL val_create(val, r_vals=default_value%r_val)
452 NULLIFY (r_last, r_first)
454 CALL get_r_val(r_val, parser, unit, default_units, c_val)
458 CALL get_r_val(r_val, parser, unit, default_units, c_val)
467 ALLOCATE (r_val_p(n_var))
470 CALL get_r_val(r_val_p(i), parser, unit, default_units, c_val)
473 IF (
ASSOCIATED(r_val_p))
THEN
481 ALLOCATE (c_val_p(1))
485 IF (.NOT.
ASSOCIATED(default_value))
THEN
486 CALL cp_abort(__location__, &
487 "no value was given and there is no default value"// &
490 cpassert(
ASSOCIATED(default_value%c_val))
491 CALL val_create(val, c_vals=default_value%c_val)
496 cpassert(n_var == -1)
497 NULLIFY (c_last, c_first)
510 ALLOCATE (c_val_p(n_var))
515 IF (
ASSOCIATED(c_val_p))
THEN
520 IF (
ASSOCIATED(default_value)) &
521 CALL cp_abort(__location__, &
522 "input variables of type lchar_t cannot have a lone keyword attribute,"// &
523 " no value is interpreted as empty string"// &
526 CALL cp_abort(__location__, &
527 "input variables of type lchar_t cannot be repeated,"// &
528 " one always represent a whole line, till the end"// &
531 ALLOCATE (c_val_p(1))
534 NULLIFY (c_last, c_first)
536 IF (c_val(1:1) == parser%quote_character)
THEN
538 c_val(1:) = c_val(2:)
539 i = index(c_val, parser%quote_character)
554 i = index(c_val, parser%quote_character)
560 CALL cp_abort(__location__, &
561 "Quotation mark found which is not the first non-blank character. "// &
562 "Possibly the first quotation mark is missing?"// &
575 cpassert(
ASSOCIATED(c_val_p))
578 cpassert(
ASSOCIATED(enum))
581 IF (.NOT.
ASSOCIATED(default_value))
THEN
583 ALLOCATE (i_val_p(0))
586 CALL cp_abort(__location__, &
587 "no value was given and there is no default value"// &
591 cpassert(
ASSOCIATED(default_value%i_val))
592 CALL val_create(val, i_vals=default_value%i_val, &
593 enum=default_value%enum)
597 NULLIFY (i_last, i_first)
610 ALLOCATE (i_val_p(n_var))
616 IF (
ASSOCIATED(i_val_p))
THEN
617 CALL val_create(val, i_vals_ptr=i_val_p, enum=enum)
621 CALL cp_abort(__location__, &
622 "type "//
cp_to_string(type_of_var)//
"unknown to the parser")
627 CALL cp_abort(__location__, &
628 "found unexpected extra argument "//trim(info)//
" at "//location)
631 CALL timestop(handle)
633 END SUBROUTINE val_create_parsing
644 SUBROUTINE get_r_val(r_val, parser, unit, default_units, c_val)
645 REAL(kind=
dp),
INTENT(OUT) :: r_val
649 CHARACTER(len=default_string_length), &
650 INTENT(INOUT) :: c_val
655 IF (
ASSOCIATED(unit))
THEN
658 IF (c_val(1:1) /=
"[" .OR. c_val(len_trim(c_val):len_trim(c_val)) /=
"]")
THEN
659 CALL cp_abort(__location__, &
660 "Invalid unit specifier or function found when parsing a number: "// &
666 IF (c_val /=
"")
THEN
674 CALL cp_abort(__location__, &
675 "Incompatible units. Defined as ("// &
676 trim(
cp_unit_desc(unit))//
") specified in input as ("// &
677 trim(
cp_unit_desc(my_unit))//
"). These units are incompatible!")
680 IF (
ASSOCIATED(unit))
THEN
682 IF (.NOT. (
ASSOCIATED(my_unit, unit)))
THEN
688 END SUBROUTINE get_r_val
various routines to log and control the output. The idea is that decisions about where to log should ...
integer function, public cp_logger_get_default_io_unit(logger)
returns the unit nr for the ionode (-1 on all other processors) skips as well checks if the procs cal...
Utility routines to read data from files. Kept as close as possible to the old parser because.
subroutine, public parser_skip_space(parser)
Skips the whitespaces.
character(len=3) function, public parser_test_next_token(parser, string_length)
Test next input object.
character(len=default_path_length+default_string_length) function, public parser_location(parser)
return a description of the part of the file actually parsed
Utility routines to read data from files. Kept as close as possible to the old parser because.
character(len=cp_unit_desc_length) function, public cp_unit_desc(unit, defaults, accept_undefined)
returns the "name" of the given unit
real(kind=dp) function, public cp_unit_to_cp2k1(value, unit, defaults, power)
transform a value to the internal cp2k units
subroutine, public cp_unit_create(unit, string)
creates a unit parsing a string
logical function, public cp_unit_compatible(ref_unit, unit)
returs true if the two units are compatible
elemental subroutine, public cp_unit_release(unit)
releases the given unit
Defines the basic variable types.
integer, parameter, public max_line_length
integer, parameter, public dp
integer, parameter, public default_string_length
Utilities for string manipulations.
character(len=1), parameter, public newline
elemental subroutine, public uppercase(string)
Convert all lower case characters in a string to upper case.
stores the default units to be used