MOAB: Mesh Oriented datABase  (version 5.4.1)
dump_geom_sets.cxx
Go to the documentation of this file.
00001 // This utility reads a MOAB HDF5 mesh file, and prints out
00002 // the list of all geometry entitysets and the parent and
00003 // child geometry entitysets of each such entityset.
00004 
00005 #include <stdio.h>
00006 #include <stdlib.h>
00007 #include <hdf5.h>
00008 #include <vector>
00009 #include <map>
00010 #include <string>
00011 
00012 // Open HDF5 file
00013 hid_t open_file( const char* name )
00014 {
00015   hid_t handle = H5Fopen( name, H5F_ACC_RDONLY, H5P_DEFAULT );
00016   if (handle < 0) {
00017     fprintf(stderr, "Cannot open file: \"%s\"\n", name );
00018     exit (1);
00019   }
00020   return handle;
00021 }
00022 
00023 // Read a scalar attribute value from an HDF5 file
00024 long read_scalar_attrib( hid_t file, const char* table, const char* attrib )
00025 {
00026   hid_t table_id = H5Dopen( file, table );
00027   if (table_id < 0) {
00028     fprintf(stderr, "Invalid file.  Data not found: \"%s\"\n", table );
00029     exit (1);
00030   }
00031   
00032   hid_t attr_id = H5Aopen_name( table_id, attrib );
00033   H5Dclose( table_id );
00034   if (attr_id < 0) {
00035     fprintf(stderr, "Invalid file.  No \"%s\" attrib on \"%s\"\n", attrib, table );
00036     exit (1);
00037   }
00038   
00039   long value;
00040   herr_t rval = H5Aread( attr_id, H5T_NATIVE_LONG, &value );
00041   H5Aclose( attr_id );
00042   if (rval < 0) {
00043     fprintf(stderr, "Failed to read \"%s\" attrib on \"%s\"\n", attrib, table );
00044     exit (2);
00045   }
00046   
00047   return value;
00048 }
00049 
00050 
00051 // Read a data table from an HDF5 file
00052 void read_data( hid_t file, const char* name, int expected_cols, std::vector<long>& data )
00053 {
00054   hid_t handle = H5Dopen( file, name );
00055   if (handle < 0) {
00056     fprintf(stderr, "Invalid file.  Data not found: \"%s\"\n", name );
00057     exit (1);
00058   }
00059 
00060   hid_t space = H5Dget_space( handle );
00061   if (space < 0) {
00062     fprintf(stderr, "Internal error accessing: \"%s\"\n", name );
00063     exit (2);
00064   }
00065   
00066   int ndims = H5Sget_simple_extent_ndims( space );
00067   if (ndims < 0) {
00068     fprintf(stderr, "Internal error accessing: \"%s\"\n", name );
00069     exit (2);
00070   }
00071   else if (ndims < 1 || ndims > 2) {
00072     fprintf(stderr, "\"%s\" is an %d-dimension table.  Corrupt file?", name, ndims );
00073     exit (2);
00074   }
00075   
00076   hsize_t dims[2] = { 0, 1 };
00077   H5Sget_simple_extent_dims( space, dims, 0 );
00078   H5Sclose( space );
00079   
00080   if (dims[1] != expected_cols) {
00081     fprintf(stderr, "Error reading \"%s\": expected %d cols, has %d\n", name, expected_cols, (int)dims[1] );
00082     exit (2);
00083   }
00084   
00085   data.resize( dims[0] * dims[1] );
00086   herr_t rval = H5Dread( handle, H5T_NATIVE_LONG, H5S_ALL, H5S_ALL, H5P_DEFAULT, &data[0] );
00087   if (rval < 0) {
00088     fprintf(stderr, "Error reading data from: \"%s\"\n", name );
00089     exit (1);
00090   }
00091   
00092   H5Dclose( handle );
00093 }
00094 
00095 // Given two vectors of the same length, create a map where the
00096 // key is taken from the first vectgor and the value is taken 
00097 // from the second vector.
00098 void create_map( const std::vector<long>& ents, 
00099                  const std::vector<long>& vals,
00100                  std::map<long,long>& map,
00101                  const char* name )
00102 {
00103   if (ents.size() != vals.size()) {
00104     fprintf(stderr, "Invalid data for tag \"%s\": mismatched table lengths.\n", name );
00105     exit (1);
00106   }
00107   
00108   std::vector<long>::const_iterator e_iter = ents.begin(), v_iter = vals.begin();
00109   for (; e_iter != ents.end(); ++e_iter, ++v_iter)
00110     map[*e_iter] = *v_iter;
00111 } 
00112 
00113 // Construct a string designator for a geometry entity given
00114 // the handle of that geometry entity and maps from handle to
00115 // dimension and handle to global id.
00116 std::string ent_from_handle( const std::map<long,long>& dimmap,
00117                              const std::map<long,long>&  idmap,
00118                              long handle )
00119 {
00120   std::string result;
00121   std::map<long,long>::const_iterator d_iter, i_iter;
00122   d_iter = dimmap.find( handle );
00123   i_iter =  idmap.find( handle );
00124   if (d_iter == dimmap.end() || i_iter == idmap.end()) 
00125     return result;
00126 
00127   switch (d_iter->second) {
00128     case 0: result += "v"; break;
00129     case 1: result += "c"; break;
00130     case 2: result += "s"; break;
00131     case 3: result += "V"; break;
00132     default:
00133       fprintf(stderr,"Invalid value in GEOM_DIMENSION tag data.\n");
00134       exit (1);
00135   }
00136   
00137   char buffer[128];
00138   sprintf(buffer, "%ld", i_iter->second );
00139   result += buffer;
00140   return result;
00141 }
00142       
00143 // Construct a string designator for list of geometry entities given
00144 // a list of handles and maps from handle to
00145 // dimension and handle to global id.
00146 std::string ent_list_from_handles( const std::map<long,long>& dimmap,
00147                                    const std::map<long,long>&  idmap,
00148                                    const std::vector<long>& vect,
00149                                    long start, 
00150                                    long stop )
00151 {
00152   std::string result;
00153   if (start >= (long)vect.size() || stop >= (long)vect.size() || stop < start) {
00154     fprintf(stderr, "Invalid set data.  Corrupt file?\n");
00155     exit(2);
00156   }
00157   std::vector<long>::const_iterator iter = vect.begin() + start+1,
00158                                      end = vect.begin() + stop+1;
00159   
00160   for (; iter != end; ++iter)
00161   {
00162     std::string tmp = ent_from_handle( dimmap, idmap, *iter );
00163     if (!tmp.empty()) {
00164       result += tmp;
00165       result += " ";
00166     }
00167     else
00168       result += "? ";
00169   }
00170   return result;
00171 }
00172 
00173 int main( int argc, char* argv[] )
00174 {
00175     // Need a file name to read
00176   if (argc != 2) {
00177     printf("Usage: %s <file>\n", argv[0] );
00178     exit(1);
00179   }
00180   
00181     // Read everything we need from the file
00182   std::vector<long> set_meta, set_child, set_parent, dim_ents, dim_vals, id_ents, id_vals;
00183   hid_t file = open_file( argv[1] );
00184   read_data( file, "/tstt/sets/list", 4, set_meta );
00185   read_data( file, "/tstt/sets/parents", 1, set_parent );
00186   read_data( file, "/tstt/sets/children", 1, set_child );
00187   read_data( file, "/tstt/tags/GEOM_DIMENSION/id_list", 1, dim_ents );
00188   read_data( file, "/tstt/tags/GEOM_DIMENSION/values", 1, dim_vals );
00189   read_data( file, "/tstt/tags/GLOBAL_ID/id_list", 1, id_ents );
00190   read_data( file, "/tstt/tags/GLOBAL_ID/values", 1, id_vals );
00191   const long startid = read_scalar_attrib( file, "/tstt/sets/list", "start_id" );
00192   H5Fclose( file );
00193   
00194     // Construct handle->dimension and handle->global_id maps.
00195   std::map<long,long> dimmap, idmap;
00196   create_map( dim_ents, dim_vals, dimmap, "GEOM_DIMENSION" );
00197   create_map(  id_ents,  id_vals,  idmap, "GLOBAL_ID" ); 
00198   
00199     // For each entity set
00200   long parent_start = -1l, child_start = -1l;
00201   printf("handle  ID     Children             Parents\n");
00202   for (unsigned i = 0; i < set_meta.size(); i += 4)
00203   {
00204       // Get name
00205     long handle = startid + i/4;
00206     std::string name = ent_from_handle( dimmap, idmap, handle );
00207     if (name.empty()) // not a geometry set
00208       continue;
00209      
00210       // Get parents and children  
00211     long  child_end = set_meta[i+1];
00212     long parent_end = set_meta[i+2];
00213     std::string children = ent_list_from_handles( dimmap, idmap,  set_child,  child_start,  child_end );
00214     std::string  parents = ent_list_from_handles( dimmap, idmap, set_parent, parent_start, parent_end );
00215      child_start =  child_end;
00216     parent_start = parent_end;
00217     
00218       // Print
00219     printf( "%6ld  %-6s %-20s %-20s\n", handle, name.c_str(), children.c_str(), parents.c_str() );
00220   }
00221   
00222   return 0;
00223 }
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines