Branch data Line data Source code
1 : : // ***************************************************************************** 2 : : /*! 3 : : \file src/IO/MeshDetect.cpp 4 : : \copyright 2012-2015 J. Bakosi, 5 : : 2016-2018 Los Alamos National Security, LLC., 6 : : 2019-2021 Triad National Security, LLC. 7 : : All rights reserved. See the LICENSE file for details. 8 : : \brief Unstructured mesh file format detection 9 : : \details Unstructured mesh file format detection functions. 10 : : */ 11 : : // ***************************************************************************** 12 : : 13 : : #include <string> 14 : : #include <fstream> 15 : : #include <stdexcept> 16 : : 17 : : #include "MeshDetect.hpp" 18 : : #include "Exception.hpp" 19 : : #include "Reader.hpp" 20 : : 21 : : namespace tk { 22 : : 23 : : MeshReaderType 24 : 821 : detectInput( const std::string& filename ) 25 : : // ***************************************************************************** 26 : : // Detect input mesh file type 27 : : //! \param[in] filename File to open and detect its type 28 : : //! \return enum specifying the mesh reader type 29 : : // ***************************************************************************** 30 : : { 31 : 1641 : std::ifstream inFile; 32 : : 33 : : // Check if file exists, throw exception if it does not 34 [ + - ]: 821 : inFile.open( filename, std::ifstream::in ); 35 [ - + ][ - - ]: 821 : ErrChk( inFile.good(), "Failed to open file: " + filename ); [ - - ][ - - ] [ - - ][ - - ] 36 : : 37 : : // Attempt to read a character, throw if it fails 38 : : // It is curious that on some systems opening a directory instead of a file 39 : : // with the above ifstream::open() call does not set the failbit. Thus we get 40 : : // here fine, so we try to read a character from it. If the read fails, we 41 : : // assume it is a directory and assume that it is in Omega_h osh file format. 42 : : // Read more at: http://stackoverflow.com/questions/9591036/ 43 : : // ifstream-open-doesnt-set-error-bits-when-argument-is-a-directory. 44 [ + - ]: 821 : inFile.get(); 45 [ + - ]: 821 : if (!inFile.good()) return MeshReaderType::OMEGA_H; 46 : : 47 : : // Close it 48 [ + - ]: 821 : inFile.close(); 49 [ - + ][ - - ]: 821 : ErrChk( !inFile.fail(), "Failed to close file: " + filename ); [ - - ][ - - ] [ - - ][ - - ] 50 : : 51 : : // Get first three letters from input file 52 [ + - ][ + - ]: 1643 : std::string s( Reader( filename ).firstline().substr(0,4) ); [ + - ] 53 : : 54 [ + + ]: 821 : if ( s.find("$Me") != std::string::npos ) { 55 : : return MeshReaderType::GMSH; 56 [ + + ][ - + ]: 826 : } else if ( s.find("CDF") != std::string::npos || 57 : : s.find("HDF") != std::string::npos ) { 58 : 806 : return MeshReaderType::EXODUSII; 59 [ + + ]: 10 : } else if ( s.find("<?x") != std::string::npos ) { 60 : : return MeshReaderType::HYPER; 61 [ + + ]: 9 : } else if ( s.find("*nd") != std::string::npos ) { 62 : : return MeshReaderType::ASC; 63 [ + + ]: 5 : } else if ( s.find(" ") != std::string::npos ) { 64 : : return MeshReaderType::UGRID; 65 [ + + ]: 4 : } else if ( s.find(" npo") != std::string::npos ) { 66 : : return MeshReaderType::RDGFLO; 67 : : } else { 68 : : try { 69 : : // cppcheck-suppress ignoredReturnValue 70 : : std::stoi(s); // try to convert to an integer 71 : 2 : } catch ( const std::invalid_argument& ) { 72 [ + - ][ + - ]: 2 : Throw( "Input mesh file type could not be determined from header: " + [ + - ][ - + ] [ - + ] 73 : : filename ); 74 : : } 75 : : // could also catch std::out_of_range, the other exception potentially 76 : : // thrown by std::stoi(), but a three-digit integer will always fit into int 77 : : 78 : : // if we got here, the above string-to-integer conversion succeeded 79 : : return MeshReaderType::NETGEN; 80 : : } 81 : : } 82 : : 83 : : MeshWriterType 84 : 18 : pickOutput( const std::string& filename ) 85 : : // ***************************************************************************** 86 : : // Determine output mesh file type 87 : : //! \param[in] filename Filename to pick its type based on extension given 88 : : //! \return enum specifying the mesh writer type 89 : : // ***************************************************************************** 90 : : { 91 : : // Get extension of input file name 92 : : std::string fn = filename; 93 [ + - ]: 18 : std::string ext( fn.substr(fn.find_last_of(".") + 1) ); 94 : : 95 [ + + ]: 18 : if ( ext == "msh" ) { 96 : : return MeshWriterType::GMSH; 97 [ + + ][ - + ]: 18 : } else if ( ext == "exo" || ext == "h5" ) { 98 : 10 : return MeshWriterType::EXODUSII; 99 [ - + ]: 4 : } else if ( ext == "mesh" ) { 100 : : return MeshWriterType::NETGEN; 101 : : } else { 102 [ - - ][ - - ]: 0 : Throw( "Output mesh file type could not be determined from extension of " [ - - ][ - - ] [ - - ][ - - ] [ - - ][ - - ] 103 : : "filename '" + filename + "'; valid extensions are: " 104 : : "'msh' for Gmsh, 'exo' or 'h5' for ExodusII, 'mesh' for Netgen's " 105 : : "neutral" ); 106 : : } 107 : : } 108 : : 109 : : } // tk::