(git:374b731)
Loading...
Searching...
No Matches
swarm.F
Go to the documentation of this file.
1!--------------------------------------------------------------------------------------------------!
2! CP2K: A general program to perform molecular dynamics simulations !
3! Copyright 2000-2024 CP2K developers group <https://cp2k.org> !
4! !
5! SPDX-License-Identifier: GPL-2.0-or-later !
6!--------------------------------------------------------------------------------------------------!
7
8! **************************************************************************************************
9!> \brief Swarm-framwork, provides a convenient master/worker architecture.
10!> \author Ole Schuett
11! **************************************************************************************************
12MODULE swarm
30 USE swarm_mpi, ONLY: swarm_mpi_finalize,&
41#include "../base/base_uses.f90"
42
43 IMPLICIT NONE
44 PRIVATE
45
46 CHARACTER(len=*), PARAMETER, PRIVATE :: moduleN = 'swarm'
47
48 PUBLIC :: run_swarm
49
50CONTAINS
51
52! **************************************************************************************************
53!> \brief Central driver routine of the swarm framework, called by cp2k_runs.F
54!> \param input_declaration ...
55!> \param root_section ...
56!> \param para_env ...
57!> \param globenv ...
58!> \param input_path ...
59!> \author Ole Schuett
60! **************************************************************************************************
61 SUBROUTINE run_swarm(input_declaration, root_section, para_env, globenv, input_path)
62 TYPE(section_type), POINTER :: input_declaration
63 TYPE(section_vals_type), POINTER :: root_section
64 TYPE(mp_para_env_type), POINTER :: para_env
65 TYPE(global_environment_type), POINTER :: globenv
66 CHARACTER(LEN=*), INTENT(IN) :: input_path
67
68 CHARACTER(len=*), PARAMETER :: routinen = 'run_swarm'
69
70 INTEGER :: handle, iw, n_workers
71 TYPE(cp_logger_type), POINTER :: logger
72
73 CALL timeset(routinen, handle)
74
75 logger => cp_get_default_logger()
76 iw = cp_print_key_unit_nr(logger, root_section, &
77 "SWARM%PRINT%MASTER_RUN_INFO", extension=".masterLog")
78
79 IF (iw > 0) WRITE (iw, "(A)") " SWARM| Ready to roll :-)"
80
81 CALL section_vals_val_get(root_section, "SWARM%NUMBER_OF_WORKERS", &
82 i_val=n_workers)
83
84 IF (n_workers == 1 .AND. para_env%num_pe == 1) THEN
85 IF (iw > 0) WRITE (iw, "(A)") " SWARM| Running in single worker mode."
86 CALL swarm_serial_driver(input_declaration, root_section, input_path, para_env, globenv)
87 ELSE
88 IF (iw > 0) WRITE (iw, "(A)") " SWARM| Running in master / workers mode."
89 !printkey iw passed on for output from swarm_mpi_init()
90 CALL swarm_parallel_driver(n_workers, input_declaration, root_section, input_path, para_env, globenv, iw)
91 END IF
92
93 CALL timestop(handle)
94 END SUBROUTINE run_swarm
95
96! **************************************************************************************************
97!> \brief Special driver for using only a single worker.
98!> \param input_declaration ...
99!> \param root_section ...
100!> \param input_path ...
101!> \param para_env ...
102!> \param globenv ...
103!> \author Ole Schuett
104! **************************************************************************************************
105 SUBROUTINE swarm_serial_driver(input_declaration, root_section, input_path, para_env, globenv)
106 TYPE(section_type), POINTER :: input_declaration
107 TYPE(section_vals_type), POINTER :: root_section
108 CHARACTER(LEN=*), INTENT(IN) :: input_path
109 TYPE(mp_para_env_type), POINTER :: para_env
110 TYPE(global_environment_type), POINTER :: globenv
111
112 INTEGER :: handle
113 LOGICAL :: should_stop
114 TYPE(swarm_master_type) :: master
115 TYPE(swarm_message_type) :: cmd, report
116 TYPE(swarm_worker_type) :: worker
117
118 CALL swarm_master_init(master, para_env, globenv, root_section, n_workers=1)
119 CALL swarm_worker_init(worker, para_env, input_declaration, root_section, &
120 input_path, worker_id=1)
121
122 CALL swarm_message_add(report, "worker_id", 1)
123 CALL swarm_message_add(report, "status", "initial_hello")
124
125 should_stop = .false.
126 DO WHILE (.NOT. should_stop)
127 CALL timeset("swarm_worker_await_reply", handle)
128 CALL swarm_master_steer(master, report, cmd)
129 CALL timestop(handle)
130 CALL swarm_message_free(report)
131 CALL swarm_worker_execute(worker, cmd, report, should_stop)
132 CALL swarm_message_free(cmd)
133 END DO
134
135 CALL swarm_message_free(report)
136 CALL swarm_worker_finalize(worker)
137 CALL swarm_master_finalize(master)
138
139 END SUBROUTINE swarm_serial_driver
140
141! **************************************************************************************************
142!> \brief Normal driver routine for parallelized runs.
143!> \param n_workers ...
144!> \param input_declaration ...
145!> \param root_section ...
146!> \param input_path ...
147!> \param para_env ...
148!> \param globenv ...
149!> \param iw ...
150!> \author Ole Schuett
151! **************************************************************************************************
152 SUBROUTINE swarm_parallel_driver(n_workers, input_declaration, root_section, input_path, para_env, globenv, iw)
153 INTEGER, INTENT(IN) :: n_workers
154 TYPE(section_type), POINTER :: input_declaration
155 TYPE(section_vals_type), POINTER :: root_section
156 CHARACTER(LEN=*), INTENT(IN) :: input_path
157 TYPE(mp_para_env_type), POINTER :: para_env
158 TYPE(global_environment_type), POINTER :: globenv
159 INTEGER, INTENT(IN) :: iw
160
161 INTEGER :: worker_id
163
164 CALL swarm_mpi_init(swarm_mpi, para_env, root_section, n_workers, worker_id, iw)
165
166 IF (ASSOCIATED(swarm_mpi%worker)) THEN
167 CALL swarm_parallel_worker_driver(swarm_mpi, input_declaration, worker_id, root_section, input_path)
168 ELSE
169 CALL swarm_parallel_master_driver(swarm_mpi, n_workers, root_section, globenv)
170 END IF
171
172 CALL swarm_mpi_finalize(swarm_mpi, root_section)
173
174 END SUBROUTINE swarm_parallel_driver
175
176! **************************************************************************************************
177!> \brief Worker's driver routine for parallelized runs.
178!> \param swarm_mpi ...
179!> \param input_declaration ...
180!> \param worker_id ...
181!> \param root_section ...
182!> \param input_path ...
183!> \author Ole Schuett
184! **************************************************************************************************
185 SUBROUTINE swarm_parallel_worker_driver(swarm_mpi, input_declaration, worker_id, root_section, input_path)
186 TYPE(swarm_mpi_type), INTENT(IN) :: swarm_mpi
187 TYPE(section_type), POINTER :: input_declaration
188 INTEGER, INTENT(IN) :: worker_id
189 TYPE(section_vals_type), POINTER :: root_section
190 CHARACTER(LEN=*), INTENT(IN) :: input_path
191
192 INTEGER :: handle
193 LOGICAL :: should_stop
194 TYPE(swarm_message_type) :: cmd, report
195 TYPE(swarm_worker_type) :: worker
196
197 CALL swarm_worker_init(worker, swarm_mpi%worker, input_declaration, &
198 root_section, input_path, worker_id=worker_id)
199
200 CALL swarm_message_add(report, "worker_id", worker_id)
201 CALL swarm_message_add(report, "status", "initial_hello")
202
203 should_stop = .false.
204 DO WHILE (.NOT. should_stop)
205 CALL timeset("swarm_worker_await_reply", handle)
206 CALL swarm_mpi_send_report(swarm_mpi, report)
207 CALL swarm_message_free(report)
209 CALL timestop(handle)
210 CALL swarm_worker_execute(worker, cmd, report, should_stop)
211 CALL swarm_message_free(cmd)
212 END DO
213
214 CALL swarm_message_free(report)
215 CALL swarm_worker_finalize(worker)
216
217 END SUBROUTINE swarm_parallel_worker_driver
218
219! **************************************************************************************************
220!> \brief Master's driver routine for parallelized runs.
221!> \param swarm_mpi ...
222!> \param n_workers ...
223!> \param root_section ...
224!> \param globenv ...
225!> \author Ole Schuett
226! **************************************************************************************************
227 SUBROUTINE swarm_parallel_master_driver(swarm_mpi, n_workers, root_section, globenv)
228 TYPE(swarm_mpi_type), INTENT(IN) :: swarm_mpi
229 INTEGER, INTENT(IN) :: n_workers
230 TYPE(section_vals_type), POINTER :: root_section
231 TYPE(global_environment_type), POINTER :: globenv
232
233 CHARACTER(len=default_string_length) :: command
234 INTEGER :: i_shutdowns, j, wid
235 LOGICAL, DIMENSION(n_workers) :: is_waiting
236 TYPE(swarm_master_type) :: master
237 TYPE(swarm_message_type) :: cmd, report
238
239 is_waiting(:) = .false.
240
241 CALL swarm_master_init(master, swarm_mpi%master, globenv, root_section, n_workers)
242
243 i_shutdowns = 0
244 j = 0
245
246 DO WHILE (i_shutdowns < n_workers)
247 ! Each iteration if the loop does s.th. different depending on j.
248 ! First (j==0) it receives one report with (blocking) MPI,
249 ! then it searches through the list is_waiting.
250 j = mod(j + 1, n_workers + 1)
251 IF (j == 0) THEN
252 CALL swarm_mpi_recv_report(swarm_mpi, report)
253 ELSE IF (is_waiting(j)) THEN
254 is_waiting(j) = .false.
255 CALL swarm_message_add(report, "worker_id", j)
256 CALL swarm_message_add(report, "status", "wait_done")
257 ELSE
258 cycle
259 END IF
260
261 CALL swarm_master_steer(master, report, cmd)
262 CALL swarm_message_free(report)
263
264 CALL swarm_message_get(cmd, "command", command)
265 IF (trim(command) == "wait") THEN
266 CALL swarm_message_get(cmd, "worker_id", wid)
267 is_waiting(wid) = .true.
268 ELSE
270 IF (trim(command) == "shutdown") i_shutdowns = i_shutdowns + 1
271 END IF
272 CALL swarm_message_free(cmd)
273 END DO
274
275 CALL swarm_master_finalize(master)
276
277 END SUBROUTINE swarm_parallel_master_driver
278
279END MODULE swarm
280
Adds an entry from a swarm-message.
Returns an entry from a swarm-message.
various routines to log and control the output. The idea is that decisions about where to log should ...
type(cp_logger_type) function, pointer, public cp_get_default_logger()
returns the default logger
routines to handle the output, The idea is to remove the decision of wheter to output and what to out...
integer function, public cp_print_key_unit_nr(logger, basis_section, print_key_path, extension, middle_name, local, log_filename, ignore_should_output, file_form, file_position, file_action, file_status, do_backup, on_file, is_new_file, mpi_io, fout)
...
Define type storing the global information of a run. Keep the amount of stored data small....
objects that represent the structure of input sections and the data contained in an input section
subroutine, public section_vals_val_get(section_vals, keyword_name, i_rep_section, i_rep_val, n_rep_val, val, l_val, i_val, r_val, c_val, l_vals, i_vals, r_vals, c_vals, explicit)
returns the requested value
Defines the basic variable types.
Definition kinds.F:23
integer, parameter, public default_string_length
Definition kinds.F:57
Interface to the message passing library MPI.
Master's routines for the swarm-framework.
subroutine, public swarm_master_finalize(master)
Finalizes the swarm master.
subroutine, public swarm_master_steer(master, report, cmd)
Central steering routine of the swarm master.
subroutine, public swarm_master_init(master, para_env, globenv, root_section, n_workers)
Initializes the swarm master.
Swarm-message, a convenient data-container for with build-in serialization.
subroutine, public swarm_message_free(msg)
Deallocates all entries contained in a swarm-message.
Handles the MPI communication of the swarm framework.
Definition swarm_mpi.F:12
subroutine, public swarm_mpi_init(swarm_mpi, world_para_env, root_section, n_workers, worker_id, iw)
Initialize MPI communicators for a swarm run.
Definition swarm_mpi.F:70
subroutine, public swarm_mpi_send_command(swarm_mpi, cmd)
Sends a command via MPI.
Definition swarm_mpi.F:365
subroutine, public swarm_mpi_recv_report(swarm_mpi, report)
Receives a report via MPI.
Definition swarm_mpi.F:346
subroutine, public swarm_mpi_recv_command(swarm_mpi, cmd)
Receives a command via MPI and broadcasts it within a worker.
Definition swarm_mpi.F:385
subroutine, public swarm_mpi_send_report(swarm_mpi, report)
Sends a report via MPI.
Definition swarm_mpi.F:324
subroutine, public swarm_mpi_finalize(swarm_mpi, root_section)
Finalizes the MPI communicators of a swarm run.
Definition swarm_mpi.F:269
Workers's routines for the swarm-framework.
subroutine, public swarm_worker_finalize(worker)
Finalizes a swarm worker.
subroutine, public swarm_worker_execute(worker, cmd, report, should_stop)
Central execute routine of the swarm worker.
subroutine, public swarm_worker_init(worker, para_env, input_declaration, root_section, input_path, worker_id)
Initializes a swarm worker.
Swarm-framwork, provides a convenient master/worker architecture.
Definition swarm.F:12
subroutine, public run_swarm(input_declaration, root_section, para_env, globenv, input_path)
Central driver routine of the swarm framework, called by cp2k_runs.F.
Definition swarm.F:62
type of a logger, at the moment it contains just a print level starting at which level it should be l...
contains the initially parsed file and the initial parallel environment
represent a section of the input file
stores all the informations relevant to an mpi environment