other/m_cmd_parser.f90
| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | !> @brief A simple command line argument parser for Fortran programs | ||
| 2 | module m_cmd_parser | ||
| 3 | private | ||
| 4 | public :: parse_cmd_args, parse_cmd_arg_pairs | ||
| 5 | |||
| 6 | contains | ||
| 7 | !> @brief Parses command line arguments and assigns them to the provided variables | ||
| 8 | !> | ||
| 9 | !> @param[inout] arg1, arg2, ..., arg10 _(optional)_ variables to assign the command line arguments to | ||
| 10 | !> | ||
| 11 | !> @note All arguments that are passed should have been given default values before calling this subroutine, otherwise they will | ||
| 12 | !> be uninitialized if the corresponding command line argument is not provided | ||
| 13 | ✗ | subroutine parse_cmd_args(arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9, arg10) | |
| 14 | implicit none | ||
| 15 | |||
| 16 | class(*), optional, intent(inout) :: arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9, arg10 | ||
| 17 | |||
| 18 | integer :: nr_args, adx | ||
| 19 | character(len=256) :: arg_value | ||
| 20 | |||
| 21 | ✗ | nr_args = command_argument_count() | |
| 22 | ✗ | do adx = 1, nr_args | |
| 23 | ✗ | call get_command_argument(adx, arg_value) | |
| 24 | |||
| 25 | ✗ | select case (adx) | |
| 26 | case (1) | ||
| 27 | ✗ | if (present(arg1)) call assign_arg(arg_value, arg1) | |
| 28 | case (2) | ||
| 29 | ✗ | if (present(arg2)) call assign_arg(arg_value, arg2) | |
| 30 | case (3) | ||
| 31 | ✗ | if (present(arg3)) call assign_arg(arg_value, arg3) | |
| 32 | case (4) | ||
| 33 | ✗ | if (present(arg4)) call assign_arg(arg_value, arg4) | |
| 34 | case (5) | ||
| 35 | ✗ | if (present(arg5)) call assign_arg(arg_value, arg5) | |
| 36 | case (6) | ||
| 37 | ✗ | if (present(arg6)) call assign_arg(arg_value, arg6) | |
| 38 | case (7) | ||
| 39 | ✗ | if (present(arg7)) call assign_arg(arg_value, arg7) | |
| 40 | case (8) | ||
| 41 | ✗ | if (present(arg8)) call assign_arg(arg_value, arg8) | |
| 42 | case (9) | ||
| 43 | ✗ | if (present(arg9)) call assign_arg(arg_value, arg9) | |
| 44 | case (10) | ||
| 45 | ✗ | if (present(arg10)) call assign_arg(arg_value, arg10) | |
| 46 | end select | ||
| 47 | end do | ||
| 48 | ✗ | end subroutine parse_cmd_args | |
| 49 | |||
| 50 | !> @brief Parses command line arguments in the form of name=value pairs and assigns them to the provided variables | ||
| 51 | !> | ||
| 52 | !> @param[in] name1, name2, ..., name10 _(optional)_ names of the command line arguments to look for | ||
| 53 | !> @param[inout] arg1, arg2, ..., arg10 _(optional)_ variables to assign the command line arguments to | ||
| 54 | !> | ||
| 55 | !> @note Command line arguments can be provided in the form of `--name=value` or `-name value` or `name value`. | ||
| 56 | !> All arguments that are passed should have been given default values before calling this subroutine, otherwise they will be | ||
| 57 | !> uninitialized if the corresponding command line argument is not provided | ||
| 58 | ✗ | subroutine parse_cmd_arg_pairs(name1, arg1, name2, arg2, name3, arg3, name4, arg4, name5, arg5, name6, arg6, name7, arg7, & | |
| 59 | name8, arg8, name9, arg9, name10, arg10) | ||
| 60 | implicit none | ||
| 61 | |||
| 62 | character(len=*), optional, intent(in) :: name1, name2, name3, name4, name5, name6, name7, name8, name9, name10 | ||
| 63 | class(*), optional, intent(inout) :: arg1, arg2, arg3, arg4, arg5, arg6, arg7, arg8, arg9, arg10 | ||
| 64 | |||
| 65 | integer :: nr_args, adx, sub_idx | ||
| 66 | character(len=256) :: arg_name, arg_value | ||
| 67 | |||
| 68 | ✗ | nr_args = command_argument_count() | |
| 69 | ✗ | adx = 1 | |
| 70 | ✗ | do while (adx <= nr_args) | |
| 71 | ✗ | call get_command_argument(adx, arg_name) | |
| 72 | ✗ | adx = adx + 1 | |
| 73 | |||
| 74 | ✗ | sub_idx = index(arg_name, '=') | |
| 75 | ✗ | if (arg_name(1:2) == '--' .and. sub_idx > 0) then | |
| 76 | ✗ | arg_value = arg_name(sub_idx + 1:) | |
| 77 | ✗ | arg_name = arg_name(3:sub_idx - 1) | |
| 78 | else | ||
| 79 | ✗ | if (arg_name(1:1) == '-') then | |
| 80 | ✗ | arg_name = arg_name(2:len(trim(arg_name))) | |
| 81 | else | ||
| 82 | arg_name = trim(arg_name) | ||
| 83 | end if | ||
| 84 | |||
| 85 | ✗ | call get_command_argument(adx, arg_value) | |
| 86 | ✗ | adx = adx + 1 | |
| 87 | end if | ||
| 88 | |||
| 89 | ✗ | if (present(name1) .and. arg_name == name1) then | |
| 90 | ✗ | if (present(arg1)) call assign_arg(arg_value, arg1) | |
| 91 | ✗ | else if (present(name2) .and. arg_name == name2) then | |
| 92 | ✗ | if (present(arg2)) call assign_arg(arg_value, arg2) | |
| 93 | ✗ | else if (present(name3) .and. arg_name == name3) then | |
| 94 | ✗ | if (present(arg3)) call assign_arg(arg_value, arg3) | |
| 95 | ✗ | else if (present(name4) .and. arg_name == name4) then | |
| 96 | ✗ | if (present(arg4)) call assign_arg(arg_value, arg4) | |
| 97 | ✗ | else if (present(name5) .and. arg_name == name5) then | |
| 98 | ✗ | if (present(arg5)) call assign_arg(arg_value, arg5) | |
| 99 | ✗ | else if (present(name6) .and. arg_name == name6) then | |
| 100 | ✗ | if (present(arg6)) call assign_arg(arg_value, arg6) | |
| 101 | ✗ | else if (present(name7) .and. arg_name == name7) then | |
| 102 | ✗ | if (present(arg7)) call assign_arg(arg_value, arg7) | |
| 103 | ✗ | else if (present(name8) .and. arg_name == name8) then | |
| 104 | ✗ | if (present(arg8)) call assign_arg(arg_value, arg8) | |
| 105 | ✗ | else if (present(name9) .and. arg_name == name9) then | |
| 106 | ✗ | if (present(arg9)) call assign_arg(arg_value, arg9) | |
| 107 | ✗ | else if (present(name10) .and. arg_name == name10) then | |
| 108 | ✗ | if (present(arg10)) call assign_arg(arg_value, arg10) | |
| 109 | end if | ||
| 110 | end do | ||
| 111 | ✗ | end subroutine parse_cmd_arg_pairs | |
| 112 | |||
| 113 | ✗ | subroutine assign_arg(arg_value, arg) | |
| 114 | class(*), intent(inout) :: arg | ||
| 115 | character(len=*), intent(in) :: arg_value | ||
| 116 | |||
| 117 | select type (arg) | ||
| 118 | type is (integer) | ||
| 119 | ✗ | read (arg_value, *) arg | |
| 120 | type is (real) | ||
| 121 | ✗ | read (arg_value, *) arg | |
| 122 | type is (double precision) | ||
| 123 | ✗ | read (arg_value, *) arg | |
| 124 | type is (character(len=*)) | ||
| 125 | ✗ | arg = arg_value | |
| 126 | type is (logical) | ||
| 127 | ✗ | read (arg_value, *) arg | |
| 128 | end select | ||
| 129 | ✗ | end subroutine assign_arg | |
| 130 | |||
| 131 | ✗ | end module | |
| 132 |