LCOV - code coverage report
Current view: top level - include/mesh - checkpoint_io.h (source / functions) Hit Total Coverage
Test: libMesh/libmesh: #4515 (9b32e2) with base 6ae6ba Lines: 3 7 42.9 %
Date: 2026-08-04 19:21:36 Functions: 3 8 37.5 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : // The libMesh Finite Element Library.
       2             : // Copyright (C) 2002-2026 Benjamin S. Kirk, John W. Peterson, Roy H. Stogner
       3             : 
       4             : // This library is free software; you can redistribute it and/or
       5             : // modify it under the terms of the GNU Lesser General Public
       6             : // License as published by the Free Software Foundation; either
       7             : // version 2.1 of the License, or (at your option) any later version.
       8             : 
       9             : // This library is distributed in the hope that it will be useful,
      10             : // but WITHOUT ANY WARRANTY; without even the implied warranty of
      11             : // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      12             : // Lesser General Public License for more details.
      13             : 
      14             : // You should have received a copy of the GNU Lesser General Public
      15             : // License along with this library; if not, write to the Free Software
      16             : // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
      17             : 
      18             : 
      19             : 
      20             : #ifndef LIBMESH_CHECKPOINT_IO_H
      21             : #define LIBMESH_CHECKPOINT_IO_H
      22             : 
      23             : 
      24             : // Local includes
      25             : #include "libmesh/compare_elems_by_level.h"
      26             : #include "libmesh/mesh_input.h"
      27             : #include "libmesh/mesh_output.h"
      28             : #include "libmesh/mesh_communication.h"
      29             : #include "libmesh/parallel_object.h"
      30             : 
      31             : // C++ includes
      32             : #include <string>
      33             : #include <vector>
      34             : 
      35             : namespace libMesh
      36             : {
      37             : // Forward declarations
      38             : class Xdr;
      39             : class CheckpointIO;
      40             : 
      41             : /**
      42             :  * split_mesh takes the given initialized/opened mesh and partitions it into nsplits pieces or
      43             :  * chunks.  It returns a CheckpointIO object that can be used to write the mesh chunks into
      44             :  * individual files (e.g. by calling checkpoint_obj.write(out_file_name)) - the number of files is
      45             :  * equal to the number of chunks.  This function supports MPI parallelism and can be used with
      46             :  * several MPI procs to speed up splitting.
      47             :  */
      48             : std::unique_ptr<CheckpointIO> split_mesh(MeshBase & mesh, processor_id_type nsplits);
      49             : 
      50             : /**
      51             :  * The CheckpointIO class can be used to write simplified restart
      52             :  * files that can be used to restart simulations that have
      53             :  * crashed.
      54             :  *
      55             :  * \author Benjamin Kirk
      56             :  * \author John Peterson
      57             :  * \author Derek Gaston
      58             :  * \author Roy Stogner
      59             :  * \date 2017
      60             :  */
      61          96 : class CheckpointIO : public MeshInput<MeshBase>,
      62             :                      public MeshOutput<MeshBase>,
      63             :                      public ParallelObject
      64             : {
      65             : public:
      66             :   // The size used for encoding all id types in this file
      67             :   typedef largest_id_type xdr_id_type;
      68             : 
      69             :   // The size type used to read header sizes (meta data information)
      70             :   typedef uint64_t header_id_type;
      71             : 
      72             :   /**
      73             :    * Constructor.  Takes a writable reference to a mesh object.
      74             :    * This is the constructor required to read a mesh.
      75             :    * The optional parameter \p binary can be used to switch
      76             :    * between ASCII (\p false, the default) or binary (\p true)
      77             :    * files.
      78             :    */
      79             :   explicit
      80             :   CheckpointIO (MeshBase &, const bool=false);
      81             : 
      82             :   /**
      83             :    * Constructor.  Takes a reference to a constant mesh object.
      84             :    * This constructor will only allow us to write the mesh.
      85             :    * The optional parameter \p binary can be used to switch
      86             :    * between ASCII (\p false, the default) or binary (\p true)
      87             :    * files.
      88             :    */
      89             :   explicit
      90             :   CheckpointIO (const MeshBase &, const bool=false);
      91             : 
      92             :   /**
      93             :    * Destructor.
      94             :    */
      95             :   virtual ~CheckpointIO ();
      96             : 
      97             :   /**
      98             :    * This method implements reading a mesh from a specified file.  If the mesh has been split for
      99             :    * running on several processors, input_name should simply be the name of the mesh split
     100             :    * directory without the "-split[n]" suffix.  The number of splits will be determined
     101             :    * automatically by the number of processes being used for the mesh at the time of reading.
     102             :    */
     103             :   virtual void read (const std::string & input_name) override;
     104             : 
     105             :   /**
     106             :    * This method implements writing a mesh to a specified file.  If the mesh has been split
     107             :    * for running on several processors, this will create a subdirectory named
     108             :    * "[name]-split[n]" where name is the given name argument and n is the number of
     109             :    * processors the mesh is split for running on.  For example:
     110             :    *
     111             :    *     unsigned int n_splits = 42;
     112             :    *     std::unique_ptr<CheckpointIO> cp = split_mesh(my_mesh, n_splits);
     113             :    *     // ...
     114             :    *     cp->write("foo.cpr");
     115             :    *
     116             :    * would create a directory named "foo.cpr-split42".
     117             :    */
     118             :   virtual void write (const std::string & name) override;
     119             : 
     120             :   /**
     121             :    * Used to remove a checkpoint directory and its corresponding files.  This effectively undoes
     122             :    * all the work done be calls to write(...).  For example, if a checkpoint configuration was
     123             :    * written via:
     124             :    *
     125             :    *     unsigned int n_splits = 42;
     126             :    *     std::unique_ptr<CheckpointIO> cp = split_mesh(my_mesh, n_splits);
     127             :    *     // ...
     128             :    *     cp->write("foo.cpr");
     129             :    *
     130             :    * then you could remove all the corresponding created files/dirs by:
     131             :    *
     132             :    *     CheckpointIO::cleanup(my_mesh, n_splits);
     133             :    *
     134             :    * Or for cases where the split configuration was determined automatically (e.g. via number of
     135             :    * running procs with distributed/parallel mesh), then you could:
     136             :    *
     137             :    *     CheckpointIO::cleanup(your_mesh, your_mesh.comm().size());
     138             :    *
     139             :    * Other remaining checkpoint split configurations for the mesh are left unmodified.
     140             :    */
     141             :   static void cleanup(const std::string & input_name, processor_id_type n_procs);
     142             : 
     143             :   /**
     144             :    * Get/Set the flag indicating if we should read/write binary.
     145             :    */
     146             :   bool   binary() const { return _binary; }
     147           0 :   bool & binary()       { return _binary; }
     148             : 
     149             :   /**
     150             :    * Get/Set the flag indicating if we should read/write binary.
     151             :    */
     152             :   bool   parallel() const { return _parallel; }
     153           0 :   bool & parallel()       { return _parallel; }
     154             : 
     155             :   /**
     156             :    * Get/Set the version string.
     157             :    */
     158        2636 :   const std::string & version () const { return _version; }
     159         940 :   std::string &       version ()       { return _version; }
     160             : 
     161             :   /**
     162             :    * \returns \p true if the current file has an XDR/XDA version that
     163             :    * matches or exceeds 1.5
     164             :    *
     165             :    * As of this version we encode any extra integer data that has been
     166             :    * attached to a mesh.
     167             :    */
     168             :   bool version_at_least_1_5() const;
     169             : 
     170             :   /**
     171             :    * \returns \p true if the current file has an XDR/XDA version that
     172             :    * matches or exceeds 1.6
     173             :    *
     174             :    * As of this version we encode runtime element topology.
     175             :    */
     176             :   bool version_at_least_1_6() const;
     177             : 
     178             :   /**
     179             :    * Get/Set the processor id or processor ids to use.
     180             :    *
     181             :    * The default processor_id to use is the processor_id() of the
     182             :    * mesh.
     183             :    *
     184             :    * This is used for m->n parallel checkpoint file writing:
     185             :    * You can force CheckpointIO to write out different partitions of a
     186             :    * mesh by setting which partitions to write from each processor here.
     187             :    */
     188             :   const std::vector<processor_id_type> & current_processor_ids() const { return _my_processor_ids; }
     189           0 :   std::vector<processor_id_type> & current_processor_ids() { return _my_processor_ids; }
     190             : 
     191             :   /**
     192             :    * Get/Set the n_processors to use
     193             :    *
     194             :    * The default n_processors to use is the n_processors() of the
     195             :    * mesh.
     196             :    *
     197             :    * This is used for m->n parallel checkpoint file writing:
     198             :    * You can force CheckpointIO to view the world as if it contains this number of
     199             :    * processors by setting it here
     200             :    */
     201             :   const processor_id_type & current_n_processors() const { return _my_n_processors; }
     202           0 :   processor_id_type & current_n_processors() { return _my_n_processors; }
     203             : 
     204             : private:
     205             :   //---------------------------------------------------------------------------
     206             :   // Write Implementation
     207             : 
     208             :   /**
     209             :    * Write subdomain name information
     210             :    */
     211             :   void write_subdomain_names(Xdr & io) const;
     212             : 
     213             :   /**
     214             :    * Write the connectivity for part of a mesh
     215             :    */
     216             :   void write_connectivity (Xdr & io,
     217             :                            const std::set<const Elem *, CompareElemIdsByLevel> & elements) const;
     218             : 
     219             :   /**
     220             :    * Write the remote_elem neighbor and child links for part of a mesh
     221             :    */
     222             :   void write_remote_elem (Xdr & io,
     223             :                           const std::set<const Elem *, CompareElemIdsByLevel> & elements) const;
     224             : 
     225             :   /**
     226             :    * Write the nodal locations for part of a mesh
     227             :    */
     228             :   void write_nodes (Xdr & io,
     229             :                     const connected_node_set_type & nodeset) const;
     230             : 
     231             :   /**
     232             :    * Write the side boundary conditions for part of a mesh
     233             :    */
     234             :   void write_bcs (Xdr & io,
     235             :                   const std::set<const Elem *, CompareElemIdsByLevel> & elements,
     236             :                   const std::vector<std::tuple<dof_id_type, unsigned short int, boundary_id_type>> & bc_triples) const;
     237             : 
     238             :   /**
     239             :    * Write the nodal boundary conditions for part of a mesh
     240             :    */
     241             :   void write_nodesets (Xdr & io,
     242             :                        const connected_node_set_type & nodeset,
     243             :                        const std::vector<std::tuple<dof_id_type, boundary_id_type>> & bc_tuples) const;
     244             : 
     245             :   /**
     246             :    * Write boundary names information (sideset and nodeset)
     247             :    */
     248             :   void write_bc_names (Xdr & io, const BoundaryInfo & info, bool is_sideset) const;
     249             : 
     250             : 
     251             :   //---------------------------------------------------------------------------
     252             :   // Read Implementation
     253             : 
     254             :   /**
     255             :    * Read header data on processor 0, then broadcast.  Returns the
     256             :    * number of processors for which parallel non-header files have
     257             :    * been written, or 0 if files were written in serial.
     258             :    */
     259             :   template <typename file_id_type>
     260             :   file_id_type read_header(const std::string & name);
     261             : 
     262             :   /**
     263             :    * Read a non-header file
     264             :    */
     265             :   template <typename file_id_type>
     266             :   void read_subfile(Xdr & io, bool expect_all_remote);
     267             : 
     268             :   /**
     269             :    * Read subdomain name information
     270             :    */
     271             :   template <typename file_id_type>
     272             :   void read_subdomain_names(Xdr & io);
     273             : 
     274             :   /**
     275             :    * Read the connectivity for a parallel, distributed mesh
     276             :    */
     277             :   template <typename file_id_type>
     278             :   void read_connectivity (Xdr & io);
     279             : 
     280             :   /**
     281             :    * Read the remote_elem neighbor and child links for a parallel, distributed mesh
     282             :    *
     283             :    * If we expect all these remote_elem links to truly be remote,
     284             :    * because we aren't doing an N -> M restart with M < N, then we set
     285             :    * \p expect_all_remote to true and test more assertions.
     286             :    */
     287             :   template <typename file_id_type>
     288             :   void read_remote_elem (Xdr & io, bool expect_all_remote);
     289             : 
     290             :   /**
     291             :    * Read the nodal locations for a parallel, distributed mesh
     292             :    */
     293             :   template <typename file_id_type>
     294             :   void read_nodes (Xdr & io);
     295             : 
     296             :   /**
     297             :    * Read the boundary conditions for a parallel, distributed mesh
     298             :    */
     299             :   template <typename file_id_type>
     300             :   void read_bcs (Xdr & io);
     301             : 
     302             :   /**
     303             :    * Read the nodeset conditions for a parallel, distributed mesh
     304             :    */
     305             :   template <typename file_id_type>
     306             :   void read_nodesets (Xdr & io);
     307             : 
     308             :   /**
     309             :    * Read boundary names information (sideset and nodeset)
     310             :    */
     311             :   template <typename file_id_type>
     312             :   void read_bc_names(Xdr & io, BoundaryInfo & info, bool is_sideset);
     313             : 
     314             :   /**
     315             :    * Read extra integers names information
     316             :    */
     317             :   template <typename file_id_type>
     318             :   void read_integers_names
     319             :     (Xdr & io,
     320             :      std::vector<std::string> & node_integer_names,
     321             :      std::vector<std::string> & elem_integer_names);
     322             : 
     323             :   /**
     324             :    * \returns The number of levels of refinement in the active mesh on
     325             :    * this processor.
     326             :    *
     327             :    * \note This includes _all_ elements on this processor even those
     328             :    * not owned by this processor!  Implemented by looping over all the
     329             :    * active elements and finding the maximum level.
     330             :    */
     331             :   unsigned int n_active_levels_in(MeshBase::const_element_iterator begin,
     332             :                                   MeshBase::const_element_iterator end) const;
     333             : 
     334             :   processor_id_type select_split_config(const std::string & input_name, header_id_type & data_size);
     335             : 
     336             :   bool _binary;
     337             :   bool _parallel;
     338             :   std::string _version;
     339             : 
     340             :   // The processor ids to write
     341             :   std::vector<processor_id_type> _my_processor_ids;
     342             : 
     343             :   // The largest processor id to write
     344             :   processor_id_type _my_n_processors;
     345             : };
     346             : 
     347             : 
     348             : } // namespace libMesh
     349             : 
     350             : #endif // LIBMESH_CHECKPOINT_IO_H

Generated by: LCOV version 1.14