Field3D
Field3DInputFile Class Reference

Provides reading of .f3d (internally, hdf5) files.Refer to using_files for examples of how to use this in your code. More...

#include <Field3DFile.h>

Inheritance diagram for Field3DInputFile:
Field3DFileBase

Public Member Functions

bool open (const std::string &filename)
 Opens the given file.
 
bool readGroupMembership (GroupMembershipMap &gpMembershipMap)
 Read the group membership for the partitions.
 
Constructors & destructor
 Field3DInputFile ()
 
virtual ~Field3DInputFile ()
 
Reading layers from disk
template<class Data_T >
Field< Data_T >::Vec readScalarLayers (const std::string &layerName=std::string("")) const
 Retrieves all the layers of scalar type and maintains their on-disk data types.
 
template<class Data_T >
Field< Data_T >::Vec readScalarLayers (const std::string &partitionName, const std::string &layerName) const
 This one allows the allows the partitionName to be passed in.
 
template<class Data_T >
Field< FIELD3D_VEC3_T< Data_T >
>::Vec 
readVectorLayers (const std::string &layerName=std::string("")) const
 Retrieves all the layers of vector type and maintains their on-disk data types.
 
template<class Data_T >
Field< FIELD3D_VEC3_T< Data_T >
>::Vec 
readVectorLayers (const std::string &partitionName, const std::string &layerName) const
 This version allows you to pass in the partition name.
 
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec readScalarLayersAs (const std::string &layerName=std::string("")) const
 Retrieves all layers for all partitions. Converts it to the given template type if needed.
 
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec readScalarLayersAs (const std::string &partitionName, const std::string &layerName) const
 Retrieves a layers given their and its parent partition's name. Converts it to the given template type if needed.
 
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec readVectorLayersAs (const std::string &layerName=std::string("")) const
 Retrieves a layers for all partitions. Converts it to the given template type if needed.
 
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec readVectorLayersAs (const std::string &partitionName, const std::string &layerName) const
 Retrieves a layers given their and its parent partition's name. Converts it to the given template type if needed.
 
Reading proxy data from disk
template<class Data_T >
EmptyField< Data_T >::Vec readProxyLayer (const std::string &partitionName, const std::string &layerName, bool isVectorLayer) const
 Retrieves a proxy version (EmptyField) of each layer .
 
template<class Data_T >
EmptyField< Data_T >::Vec readProxyScalarLayers (const std::string &name=std::string("")) const
 Retrieves a proxy version (EmptyField) of each scalar layer.
 
template<class Data_T >
EmptyField< Data_T >::Vec readProxyVectorLayers (const std::string &name=std::string("")) const
 Retrieves a proxy version (EmptyField) of each vector layer.
 
Internal utility methods
herr_t parsePartition (hid_t loc_id, const std::string partitionName)
 Gets called from parsePartitions. Not intended for any other use.
 
herr_t parseLayer (hid_t loc_id, const std::string &partitionName, const std::string &layerName)
 Gets called from parsePartitions. Not intended for any other use.
 
- Public Member Functions inherited from Field3DFileBase
void clear ()
 Clear the data structures and close the file.
 
bool close ()
 Closes the file. No need to call this unless you specifically want to close the file early. It will close once the File object goes out of scope.
 
FieldMetadata< Field3DFileBase > & metadata ()
 accessor to the m_metadata class
 
const FieldMetadata
< Field3DFileBase > & 
metadata () const
 Read only access to the m_metadata class.
 
virtual void metadataHasChanged (const std::string &)
 This function should implemented by concrete classes to get the callback when metadata changes.
 
 Field3DFileBase ()
 
virtual ~Field3DFileBase ()=0
 Pure virtual destructor to ensure we never instantiate this class.
 
void getPartitionNames (std::vector< std::string > &names) const
 Gets the names of all the partitions in the file.
 
void getScalarLayerNames (std::vector< std::string > &names, const std::string &partitionName) const
 Gets the names of all the scalar layers in a given partition.
 
void getVectorLayerNames (std::vector< std::string > &names, const std::string &partitionName) const
 Gets the names of all the vector layers in a given partition.
 
File::Partition::Ptr getPartition (const std::string &partitionName) const
 Returns a pointer to the given partition.
 
std::string intPartitionName (const std::string &partitionName, const std::string &layerName, FieldRes::Ptr field)
 Returns a unique partition name given the requested name. This ensures that partitions with matching mappings get the same name but each subsequent differing mapping gets a new, separate name.
 
std::string removeUniqueId (const std::string &partitionName) const
 Strips any unique identifiers from the partition name and returns the original name.
 
void addGroupMembership (const GroupMembershipMap &groupMembers)
 Add to the group membership.
 
void printHierarchy () const
 

Private Member Functions

template<class Data_T >
Field< Data_T >::Ptr readLayer (const std::string &intPartitionName, const std::string &layerName, bool isVectorLayer) const
 This call does the actual reading of a layer. Notice that it expects a unique -internal- partition name.
 
bool readMetadata (hid_t metadata_id, FieldBase::Ptr field) const
 Read metadata for this layer.
 
bool readMetadata (hid_t metadata_id)
 Read global metadata for this file.
 
bool readPartitionAndLayerInfo ()
 Sets up all the partitions and layers, but does not load any data.
 
template<class Data_T >
Field< Data_T >::Ptr readScalarLayer (const std::string &intPartitionName, const std::string &layerName) const
 Retrieves a single layer given its and its parent partition's name. Maintains the on-disk data types.
 
template<class Data_T >
Field< FIELD3D_VEC3_T< Data_T >
>::Ptr 
readVectorLayer (const std::string &intPartitionName, const std::string &layerName) const
 Retrieves a single layer given its and its parent partition's name. Maintains the on-disk data types.
 

Private Attributes

std::string m_filename
 Filename, only to be set by open().
 

Additional Inherited Members

- Public Types inherited from Field3DFileBase
typedef std::map< std::string,
std::string > 
GroupMembershipMap
 
- Protected Types inherited from Field3DFileBase
typedef std::map< std::string,
int > 
PartitionCountMap
 
typedef std::vector
< File::Partition::Ptr
PartitionList
 
- Protected Member Functions inherited from Field3DFileBase
void closeInternal ()
 Closes the file if open.
 
File::Partition::Ptr partition (const std::string &partitionName)
 Returns a pointer to the given partition.
 
File::Partition::Ptr partition (const std::string &partitionName) const
 Returns a pointer to the given partition.
 
void getIntPartitionNames (std::vector< std::string > &names) const
 Gets the names of all the -internal- partitions in the file.
 
void getIntScalarLayerNames (std::vector< std::string > &names, const std::string &intPartitionName) const
 Gets the names of all the scalar layers in a given partition, but assumes that partition name is the -internal- partition name.
 
void getIntVectorLayerNames (std::vector< std::string > &names, const std::string &intPartitionName) const
 Gets the names of all the vector layers in a given partition, but assumes that partition name is the -internal- partition name.
 
int numIntPartitions (const std::string &partitionName) const
 Returns the number of internal partitions for a given partition name.
 
std::string makeIntPartitionName (const std::string &partitionsName, int i) const
 Makes an internal partition name given the external partition name. Effectively just tacks on .X to the name, where X is the number.
 
- Protected Attributes inherited from Field3DFileBase
hid_t m_file
 The hdf5 id of the current file. Will be -1 if no file is open.
 
GroupMembershipMap m_groupMembership
 Keeps track of group membership for each layer of partition name. The key is the "group" and the value is a space separated list of "partitionName.0:Layer1 partitionName.1:Layer0 ...".
 
std::vector< LayerInfom_layerInfo
 This stores layer info.
 
FieldMetadata< Field3DFileBasem_metadata
 metadata
 
PartitionCountMap m_partitionCount
 Contains a counter for each partition name. This is used to keep multiple fields with the same name unique in the file.
 
std::vector< std::string > m_partitionNames
 This stores partition names.
 
PartitionList m_partitions
 Vector of partitions.
 

Detailed Description

Provides reading of .f3d (internally, hdf5) files.

Refer to using_files for examples of how to use this in your code.

Note
We distinguish between scalar and vector layers even though both are templated. A scalarField<float> layer is interchangeable with a scalarField<double> (conceptually) but not with a scalar<V3f>, and thus not with vectorField<float>.

Definition at line 431 of file Field3DFile.h.

Constructor & Destructor Documentation

Field3DInputFile::Field3DInputFile ( )

Definition at line 561 of file Field3DFile.cpp.

{
// Empty
}
Field3DInputFile::~Field3DInputFile ( )
virtual

Definition at line 568 of file Field3DFile.cpp.

References Field3DFileBase::clear().

{
clear();
}

Member Function Documentation

template<class Data_T >
Field< Data_T >::Vec Field3DInputFile::readScalarLayers ( const std::string &  layerName = std::string("")) const

Retrieves all the layers of scalar type and maintains their on-disk data types.

Parameters
layerNameIf a string is passed in, only layers of that name will be read from disk.

Definition at line 769 of file Field3DFile.h.

References Field3DFileBase::getIntPartitionNames(), and Field3DFileBase::getIntScalarLayerNames().

{
using namespace std;
typedef typename Field<Data_T>::Ptr FieldPtr;
typedef typename Field<Data_T>::Vec FieldList;
FieldList ret;
std::vector<std::string> parts;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
std::vector<std::string> layers;
for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
// Only read if it matches the name
if ((name.length() == 0) || (*l == name)) {
FieldPtr mf = readScalarLayer<Data_T>(*p, *l);
if (mf) {
ret.push_back(mf);
}
}
}
}
return ret;
}
template<class Data_T >
Field< Data_T >::Vec Field3DInputFile::readScalarLayers ( const std::string &  partitionName,
const std::string &  layerName 
) const

This one allows the allows the partitionName to be passed in.

Definition at line 801 of file Field3DFile.h.

References Field3DFileBase::getIntPartitionNames(), Field3DFileBase::getIntScalarLayerNames(), and Field3DFileBase::removeUniqueId().

{
using namespace std;
typedef typename Field<Data_T>::Ptr FieldPtr;
typedef typename Field<Data_T>::Vec FieldList;
FieldList ret;
if ((layerName.length() == 0) || (partitionName.length() == 0))
return ret;
std::vector<std::string> parts;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
std::vector<std::string> layers;
if (removeUniqueId(*p) == partitionName) {
for (vector<string>::iterator l = layers.begin();
l != layers.end(); ++l) {
// Only read if it matches the name
if (*l == layerName) {
FieldPtr mf = readScalarLayer<Data_T>(*p, *l);
if (mf)
ret.push_back(mf);
}
}
}
}
return ret;
}
template<class Data_T >
Field< FIELD3D_VEC3_T< Data_T > >::Vec Field3DInputFile::readVectorLayers ( const std::string &  layerName = std::string("")) const

Retrieves all the layers of vector type and maintains their on-disk data types.

Parameters
layerNameIf a string is passed in, only layers of that name will be read from disk.

Definition at line 840 of file Field3DFile.h.

References Field3DFileBase::getIntPartitionNames(), and Field3DFileBase::getIntVectorLayerNames().

{
using namespace std;
typedef typename Field<FIELD3D_VEC3_T<Data_T> >::Ptr FieldPtr;
typedef typename Field<FIELD3D_VEC3_T<Data_T> >::Vec FieldList;
FieldList ret;
std::vector<std::string> parts;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
std::vector<std::string> layers;
for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
// Only read if it matches the name
if ((name.length() == 0) || (*l == name)) {
FieldPtr mf = readVectorLayer<Data_T>(*p, *l);
if (mf)
ret.push_back(mf);
}
}
}
return ret;
}
template<class Data_T >
Field< FIELD3D_VEC3_T< Data_T > >::Vec Field3DInputFile::readVectorLayers ( const std::string &  partitionName,
const std::string &  layerName 
) const

This version allows you to pass in the partition name.

Definition at line 872 of file Field3DFile.h.

References Field3DFileBase::getIntPartitionNames(), Field3DFileBase::getIntVectorLayerNames(), and Field3DFileBase::removeUniqueId().

{
using namespace std;
typedef typename Field<FIELD3D_VEC3_T<Data_T> >::Ptr FieldPtr;
typedef typename Field<FIELD3D_VEC3_T<Data_T> >::Vec FieldList;
FieldList ret;
if ((layerName.length() == 0) || (partitionName.length() == 0))
return ret;
std::vector<std::string> parts;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
std::vector<std::string> layers;
if (removeUniqueId(*p) == partitionName) {
for (vector<string>::iterator l = layers.begin();
l != layers.end(); ++l) {
// Only read if it matches the name
if (*l == layerName) {
FieldPtr mf = readVectorLayer<Data_T>(*p, *l);
if (mf)
ret.push_back(mf);
}
}
}
}
return ret;
}
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec Field3DInputFile::readScalarLayersAs ( const std::string &  layerName = std::string("")) const

Retrieves all layers for all partitions. Converts it to the given template type if needed.

Definition at line 990 of file Field3DFile.h.

References field_dynamic_cast().

{
typedef typename Field<Data_T>::Vec FieldList;
typedef typename Field_T<Data_T>::Vec TypedFieldList;
// First, read the layers as-is
FieldList originals;
originals = readScalarLayers<Data_T>(layerName);
// Loop over fields, converting if needed
TypedFieldList output;
typename FieldList::iterator i = originals.begin();
for (; i != originals.end(); ++i) {
typename Field_T<Data_T>::Ptr targetField;
targetField = field_dynamic_cast<Field_T<Data_T> >(*i);
if (targetField) {
output.push_back(targetField);
} else {
typename Field_T<Data_T>::Ptr newTarget(new Field_T<Data_T>);
newTarget->name = (*i)->name;
newTarget->attribute = (*i)->attribute;
newTarget->copyMetadata(*i);
newTarget->copyFrom(*i);
output.push_back(newTarget);
}
}
return output;
}
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec Field3DInputFile::readScalarLayersAs ( const std::string &  partitionName,
const std::string &  layerName 
) const

Retrieves a layers given their and its parent partition's name. Converts it to the given template type if needed.

Definition at line 1024 of file Field3DFile.h.

References field_dynamic_cast().

{
typedef typename Field<Data_T>::Vec FieldList;
typedef typename Field_T<Data_T>::Vec TypedFieldList;
// First, read the layers as-is
FieldList originals;
originals = readScalarLayers<Data_T>(partitionName, layerName);
// Loop over fields, converting if needed
TypedFieldList output;
typename FieldList::iterator i = originals.begin();
for (; i != originals.end(); ++i) {
typename Field_T<Data_T>::Ptr targetField;
targetField = field_dynamic_cast<Field_T<Data_T> >(*i);
if (targetField) {
output.push_back(targetField);
} else {
typename Field_T<Data_T>::Ptr newTarget(new Field_T<Data_T>);
newTarget->name = (*i)->name;
newTarget->attribute = (*i)->attribute;
newTarget->copyMetadata(**i);
newTarget->copyFrom(*i);
output.push_back(newTarget);
}
}
return output;
}
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec Field3DInputFile::readVectorLayersAs ( const std::string &  layerName = std::string("")) const

Retrieves a layers for all partitions. Converts it to the given template type if needed.

Definition at line 1059 of file Field3DFile.h.

References field_dynamic_cast().

{
typedef typename Field<Data_T>::Vec FieldList;
typedef typename Field_T<Data_T>::Vec TypedFieldList;
// First, read the layers as-is
FieldList originals;
originals = readVectorLayers<Data_T>(layerName);
// Loop over fields, converting if needed
TypedFieldList output;
typename FieldList::iterator i = originals.begin();
for (; i != originals.end(); ++i) {
typename Field_T<Data_T>::Ptr targetField;
targetField = field_dynamic_cast<Field_T<Data_T> >(*i);
if (targetField) {
output.push_back(targetField);
} else {
typename Field_T<Data_T>::Ptr newTarget(new Field_T<Data_T>);
newTarget->name = (*i)->name;
newTarget->attribute = (*i)->attribute;
newTarget->copyMetadata(*i);
newTarget->copyFrom(*i);
output.push_back(newTarget);
}
}
return output;
}
template<template< typename T > class Field_T, class Data_T >
Field_T< Data_T >::Vec Field3DInputFile::readVectorLayersAs ( const std::string &  partitionName,
const std::string &  layerName 
) const

Retrieves a layers given their and its parent partition's name. Converts it to the given template type if needed.

Definition at line 1093 of file Field3DFile.h.

References field_dynamic_cast().

{
typedef typename Field<Data_T>::Vec FieldList;
typedef typename Field_T<Data_T>::Vec TypedFieldList;
// First, read the layers as-is
FieldList originals;
originals = readVectorLayers<Data_T>(partitionName, layerName);
// Loop over fields, converting if needed
TypedFieldList output;
typename FieldList::iterator i = originals.begin();
for (; i != originals.end(); ++i) {
typename Field_T<Data_T>::Ptr targetField;
targetField = field_dynamic_cast<Field_T<Data_T> >(*i);
if (targetField) {
output.push_back(targetField);
} else {
typename Field_T<Data_T>::Ptr newTarget(new Field_T<Data_T>);
newTarget->name = (*i)->name;
newTarget->attribute = (*i)->attribute;
newTarget->copyMetadata(*i);
newTarget->copyFrom(*i);
output.push_back(newTarget);
}
}
return output;
}
template<class Data_T >
EmptyField< Data_T >::Vec Field3DInputFile::readProxyLayer ( const std::string &  partitionName,
const std::string &  layerName,
bool  isVectorLayer 
) const

Retrieves a proxy version (EmptyField) of each layer .

Note
Although the call is templated, all fields are read, regardless of bit depth.
Parameters
nameIf a string is passed in, only layers of that name will be read from disk.

Definition at line 1128 of file Field3DFile.h.

References FieldBase::attribute, Field3DFileBase::getIntPartitionNames(), Field3DFileBase::getIntScalarLayerNames(), Field3DFileBase::getIntVectorLayerNames(), Field3DFileBase::m_file, File::Layer::name, FieldBase::name, File::Layer::parent, Field3DFileBase::partition(), Msg::print(), Hdf5Util::readAttribute(), readMetadata(), Field3DFileBase::removeUniqueId(), FieldRes::setMapping(), ResizableField< Data_T >::setSize(), and Msg::SevWarning.

{
using namespace boost;
using namespace std;
using namespace Hdf5Util;
// Instantiate a null pointer for easier code reading
typename EmptyField<Data_T>::Vec emptyList, output;
if ((layerName.length() == 0) || (partitionName.length() == 0))
return emptyList;
std::vector<std::string> parts, layers;
bool foundPartition = false;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
if (removeUniqueId(*p) == partitionName) {
foundPartition = true;
if (isVectorLayer) {
} else {
}
for (vector<string>::iterator l = layers.begin();
l != layers.end(); ++l) {
if (*l == layerName) {
// Find the partition
if (!part) {
Msg::print(Msg::SevWarning, "Couldn't find partition: " + *p);
return emptyList;
}
// Find the layer
const File::Layer *layer;
if (isVectorLayer)
layer = part->vectorLayer(layerName);
else
layer = part->scalarLayer(layerName);
if (!layer) {
Msg::print(Msg::SevWarning, "Couldn't find layer: " + layerName);
return emptyList;
}
// Open the layer group
string layerPath = layer->parent + "/" + layer->name;
H5ScopedGopen layerGroup(m_file, layerPath.c_str());
if (layerGroup.id() < 0) {
Msg::print(Msg::SevWarning, "Couldn't find layer group "
+ layerName + " in .f3d file ");
return emptyList;
}
// Read the extents and data window
Box3i extents, dataW;
if (!readAttribute(layerGroup, "extents", 6, extents.min.x)) {
return emptyList;
}
if (!readAttribute(layerGroup, "data_window", 6, dataW.min.x)) {
return emptyList;
}
// Construct the field and load the data
field->setSize(extents, dataW);
// read the metadata
string metadataPath = layerPath + "/metadata";
H5ScopedGopen metadataGroup(m_file, metadataPath.c_str());
if (metadataGroup.id() > 0) {
readMetadata(metadataGroup.id(), field);
}
// ... Set the name of the field so it's possible to
// ... re-create the file
field->name = partitionName;
field->attribute = layerName;
field->setMapping(part->mapping);
// Add field to output
output.push_back(field);
}
}
}
}
if (!foundPartition) {
Msg::print(Msg::SevWarning, "Couldn't find partition: " + partitionName);
return emptyList;
}
return output;
}
template<class Data_T >
EmptyField< Data_T >::Vec Field3DInputFile::readProxyScalarLayers ( const std::string &  name = std::string("")) const

Retrieves a proxy version (EmptyField) of each scalar layer.

Note
Although the call is templated, all fields are read, regardless of bit depth.
Parameters
nameIf a string is passed in, only layers of that name will be read from disk.

Definition at line 1225 of file Field3DFile.h.

References Field3DFileBase::getPartitionNames(), and Field3DFileBase::getScalarLayerNames().

{
using namespace std;
typedef typename EmptyField<Data_T>::Ptr FieldPtr;
typedef std::vector<FieldPtr> FieldList;
FieldList ret;
std::vector<std::string> parts;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
std::vector<std::string> layers;
getScalarLayerNames(layers, *p);
for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
// Only read if it matches the name
if ((name.length() == 0) || (*l == name)) {
FieldList f = readProxyLayer<Data_T>(*p, *l, false);
for (typename FieldList::iterator i = f.begin(); i != f.end(); ++i) {
if (*i) {
ret.push_back(*i);
}
}
}
}
}
return ret;
}
template<class Data_T >
EmptyField< Data_T >::Vec Field3DInputFile::readProxyVectorLayers ( const std::string &  name = std::string("")) const

Retrieves a proxy version (EmptyField) of each vector layer.

Note
Although the call is templated, all fields are read, regardless of bit depth.
Parameters
nameIf a string is passed in, only layers of that name will be read from disk.

Definition at line 1260 of file Field3DFile.h.

References Field3DFileBase::getPartitionNames(), and Field3DFileBase::getVectorLayerNames().

{
using namespace std;
typedef typename EmptyField<Data_T>::Ptr FieldPtr;
typedef std::vector<FieldPtr> FieldList;
FieldList ret;
std::vector<std::string> parts;
for (vector<string>::iterator p = parts.begin(); p != parts.end(); ++p) {
std::vector<std::string> layers;
getVectorLayerNames(layers, *p);
for (vector<string>::iterator l = layers.begin(); l != layers.end(); ++l) {
// Only read if it matches the name
if ((name.length() == 0) || (*l == name)) {
FieldList f = readProxyLayer<Data_T>(*p, *l, true);
for (typename FieldList::iterator i = f.begin(); i != f.end(); ++i) {
if (*i) {
ret.push_back(*i);
}
}
}
}
}
return ret;
}
bool Field3DInputFile::open ( const std::string &  filename)

Opens the given file.

Returns
Whether successful

Definition at line 575 of file Field3DFile.cpp.

References Field3DFileBase::clear(), Field3DFileBase::close(), Hdf5Util::H5Base::id(), Field3DFileBase::m_file, m_filename, Msg::print(), Hdf5Util::readAttribute(), readMetadata(), readPartitionAndLayerInfo(), Msg::SevWarning, and Exc::Exception::what().

{
clear();
bool success = true;
m_filename = filename;
try {
string version;
// Throws exceptions if the file doesn't exist.
// This was added because H5Fopen prints out a lot of junk
// to the terminal.
checkFile(filename);
m_file = H5Fopen(filename.c_str(), H5F_ACC_RDONLY, H5P_DEFAULT);
if (m_file < 0)
throw NoSuchFileException(filename);
int fileVersion[3];
try {
if (!readAttribute(m_file, k_versionAttrName, 3, fileVersion[0])) {
//Msg::print(Msg::SevWarning, "Missing version_number attribute");
} else {
if (!isSupportedFileVersion(fileVersion, k_minFileVersion)) {
stringstream versionStr;
versionStr << fileVersion[0] << "."
<< fileVersion[1] << "."
<< fileVersion[2];
throw UnsupportedVersionException(versionStr.str());
}
}
}
catch (MissingAttributeException &e) {
//Msg::print(Msg::SevWarning, "Missing version_number attribute");
}
try {
if (H5Lexists(m_file, "field3d_global_metadata", H5P_DEFAULT)) {
// read the metadata
H5ScopedGopen metadataGroup(m_file, "field3d_global_metadata");
if (metadataGroup.id() > 0) {
readMetadata(metadataGroup.id());
}
}
}
catch (...) {
"Unknown error when reading file metadata ");
//throw BadFileHierarchyException(filename);
}
try {
success = false;
}
}
catch (MissingGroupException &e) {
Msg::print(Msg::SevWarning, "Missing group: " + string(e.what()));
throw BadFileHierarchyException(filename);
}
catch (ReadMappingException &e) {
Msg::print(Msg::SevWarning, "Couldn't read mapping for partition: "
+ string(e.what()));
throw BadFileHierarchyException(filename);
}
catch (Exception &e) {
Msg::print(Msg::SevWarning, "Unknown error when reading file hierarchy: "
+ string(e.what()));
throw BadFileHierarchyException(filename);
}
catch (...) {
"Unknown error when reading file hierarchy. ");
throw BadFileHierarchyException(filename);
}
}
catch (NoSuchFileException &e) {
Msg::print(Msg::SevWarning, "Couldn't open file: "
+ string(e.what()) );
success = false;
}
catch (MissingAttributeException &e) {
"In file: " + filename + " - "
+ string(e.what()) );
success = false;
}
catch (UnsupportedVersionException &e) {
"In file: " + filename + " - File version can not be read: "
+ string(e.what()));
success = false;
}
catch (BadFileHierarchyException &e) {
"In file: " + filename + " - Bad file hierarchy. ");
success = false;
}
catch (...) {
"In file: " + filename + " Unknown exception ");
success = false;
}
if (!success)
close();
return success;
}
herr_t Field3DInputFile::parsePartition ( hid_t  loc_id,
const std::string  partitionName 
)

Gets called from parsePartitions. Not intended for any other use.

Definition at line 784 of file Field3DFile.cpp.

References Field3DFileBase::m_partitionNames.

Referenced by InputFile::parsePartitions().

{
// Add the partition ---
m_partitionNames.push_back(string(itemName));
return 0;
}
herr_t Field3DInputFile::parseLayer ( hid_t  layerGroup,
const std::string &  partitionName,
const std::string &  layerName 
)

Gets called from parsePartitions. Not intended for any other use.

Note
Don't throw exceptions into the hdf5 lib.
Todo:
Set some sort of flag if we fail during this call. We can't throw exceptions inside hdf5.

Definition at line 798 of file Field3DFile.cpp.

References Field3DFileBase::m_layerInfo, Msg::print(), Hdf5Util::readAttribute(), and Msg::SevWarning.

Referenced by InputFile::parseLayers().

{
int components;
if (!readAttribute(layerGroup, string("components"), 1, components)) {
Msg::print(Msg::SevWarning, "Couldn't read components attribute for layer "
+ partitionName + "/" + layerName);
return 0;
}
LayerInfo linfo(partitionName,layerName,components);
m_layerInfo.push_back(linfo);
return 0;
}
bool Field3DInputFile::readGroupMembership ( GroupMembershipMap gpMembershipMap)

Read the group membership for the partitions.

Definition at line 1039 of file Field3DFile.cpp.

References Hdf5Util::H5Base::id(), Field3DFileBase::m_file, Field3DFileBase::m_groupMembership, Msg::print(), Hdf5Util::readAttribute(), Field3DFileBase::removeUniqueId(), and Msg::SevWarning.

{
if (!H5Lexists(m_file, "field3d_group_membership", H5P_DEFAULT)) {
return false;
}
H5ScopedGopen memberGroup(m_file, "field3d_group_membership");
if (memberGroup < 0) {
return false;
}
typedef boost::tokenizer<boost::char_separator<char> > Tok;
hsize_t num_attrs = H5Aget_num_attrs(memberGroup);
if (num_attrs > 0) {
for (hsize_t idx=0; idx < num_attrs ; ++idx) {
H5ScopedAopenIdx attrIdx(memberGroup, idx);
size_t len = H5Aget_name(attrIdx.id(), 0, NULL);
if (len>0) {
char *name = new char[len+1];
if (H5Aget_name(attrIdx.id(), len+1, name) > 0) {
if (string(name) == "is_field3d_group_membership")
continue;
H5ScopedAopen attr(memberGroup, name, H5P_DEFAULT);
H5ScopedAget_space attrSpace(attr);
H5ScopedAget_type attrType(attr);
H5T_class_t typeClass = H5Tget_class(attrType);
if (typeClass == H5T_STRING) {
string value;
if (!readAttribute(memberGroup, name, value)) {
"Failed to read group membership data "
+ string(name));
continue;
}
{
boost::char_separator<char> sep(" :");
Tok tok(value, sep);
string new_value;
for(Tok::iterator beg=tok.begin(); beg!=tok.end();){
string fieldgroup = *beg; ++beg;
fieldgroup = removeUniqueId(fieldgroup) + ":" + *beg; ++beg;
new_value += fieldgroup + " ";
}
m_groupMembership[name] = value;
gpMembershipMap[name] = new_value;
}
}
}
}
}
}
return true;
}
template<class Data_T >
Field< Data_T >::Ptr Field3DInputFile::readScalarLayer ( const std::string &  intPartitionName,
const std::string &  layerName 
) const
private

Retrieves a single layer given its and its parent partition's name. Maintains the on-disk data types.

Definition at line 1295 of file Field3DFile.h.

References Field3DFileBase::intPartitionName().

{
return readLayer<Data_T>(intPartitionName, layerName, false);
}
template<class Data_T >
Field< FIELD3D_VEC3_T< Data_T > >::Ptr Field3DInputFile::readVectorLayer ( const std::string &  intPartitionName,
const std::string &  layerName 
) const
private

Retrieves a single layer given its and its parent partition's name. Maintains the on-disk data types.

Definition at line 1305 of file Field3DFile.h.

References Field3DFileBase::intPartitionName().

{
return readLayer<FIELD3D_VEC3_T<Data_T> >(intPartitionName, layerName, true);
}
template<class Data_T >
Field< Data_T >::Ptr Field3DInputFile::readLayer ( const std::string &  intPartitionName,
const std::string &  layerName,
bool  isVectorLayer 
) const
private

This call does the actual reading of a layer. Notice that it expects a unique -internal- partition name.

Definition at line 911 of file Field3DFile.h.

References Field3DFileBase::m_file, m_filename, Field3DFileBase::partition(), Msg::print(), Hdf5Util::readAttribute(), readMetadata(), Field3DFileBase::removeUniqueId(), and Msg::SevWarning.

{
using namespace boost;
using namespace std;
using namespace Hdf5Util;
// Instantiate a null pointer for easier code reading
typename Field<Data_T>::Ptr nullPtr;
// Find the partition
if (!part) {
Msg::print(Msg::SevWarning, "Couldn't find partition: " + intPartitionName);
return nullPtr;
}
// Find the layer in the partition
const File::Layer *l;
if (isVectorLayer)
l = part->vectorLayer(layerName);
else
l = part->scalarLayer(layerName);
if (!l) {
Msg::print(Msg::SevWarning, "Couldn't find layer: " + layerName );
return nullPtr;
}
// Open the layer group
string layerPath = l->parent + "/" + l->name;
H5ScopedGopen layerGroup(m_file, layerPath.c_str());
if (layerGroup.id() < 0) {
Msg::print(Msg::SevWarning, "Couldn't find layer group " + layerName
+ " in .f3d file ");
return nullPtr;
}
// Get the class name
string className;
if (!readAttribute(layerGroup.id(), "class_name", className)) {
Msg::print(Msg::SevWarning, "Couldn't find class_name attrib in layer " +
layerName);
return nullPtr;
}
// Construct the field and load the data
typename Field<Data_T>::Ptr field;
field = readField<Data_T>(className, layerGroup.id(), m_filename, layerPath);
if (!field) {
#if 0 // This isn't really an error
Msg::print(Msg::SevWarning, "Couldn't read the layer data of layer: "
+ layerName);
#endif
return nullPtr;
}
// read the metadata
string metadataPath = layerPath + "/metadata";
H5ScopedGopen metadataGroup(m_file, metadataPath.c_str());
if (metadataGroup.id() > 0) {
readMetadata(metadataGroup.id(), field);
}
// Set the name of the field so it's possible to re-create the file
field->attribute = layerName;
field->setMapping(part->mapping);
return field;
}
bool Field3DInputFile::readPartitionAndLayerInfo ( )
private

Sets up all the partitions and layers, but does not load any data.

Definition at line 692 of file Field3DFile.cpp.

References InputFile::ParseLayersInfo::file, Hdf5Util::H5Base::id(), Field3DFileBase::m_file, Field3DFileBase::m_layerInfo, Field3DFileBase::m_partitionNames, Field3DFileBase::m_partitions, File::Layer::name, File::Layer::parent, InputFile::parseLayers(), InputFile::parsePartitions(), Field3DFileBase::partition(), InputFile::ParseLayersInfo::partitionName, Msg::print(), readFieldMapping(), and Msg::SevWarning.

Referenced by open().

{
using namespace InputFile;
// First, find the partitions ---
herr_t status;
status = H5Literate(m_file, H5_INDEX_NAME, H5_ITER_NATIVE, NULL,
&parsePartitions, this);
// Get the partition names to store
m_partitions.clear();
for (size_t i=0; i < m_partitionNames.size(); i++) {
part->name = m_partitionNames[i];
m_partitions.push_back(part);
}
// For each partition, find its mapping ---
for (PartitionList::iterator i = m_partitions.begin();
i != m_partitions.end(); ++i) {
// Open the partition
H5ScopedGopen partitionGroup(m_file, (**i).name);
string mappingPath = "/" + (**i).name + "/" + k_mappingStr;
// Open up the mapping group
H5ScopedGopen mappingGroup(m_file, mappingPath);
if (mappingGroup.id() < 0)
throw MissingGroupException((**i).name + "/" + k_mappingStr);
// Try to build a mapping from it
mapping = readFieldMapping(mappingGroup.id());
if (!mapping) {
Msg::print(Msg::SevWarning, "Got a null pointer when reading mapping");
throw ReadMappingException((**i).name);
}
// Attach the mapping to the partition
(**i).mapping = mapping;
}
// ... And then find its layers ---
for (PartitionList::const_iterator i = m_partitions.begin();
i != m_partitions.end(); ++i) {
// Open the partition
H5ScopedGopen partitionGroup(m_file, (**i).name);
// Set up the info struct for the callback
info.file = this;
info.partitionName = (**i).name;
m_layerInfo.clear();
status = H5Literate(partitionGroup.id(), H5_INDEX_NAME, H5_ITER_NATIVE,
NULL, &parseLayers, &info);
//set the layer information on the partitions here
for (std::vector<LayerInfo>::iterator i = m_layerInfo.begin();
i != m_layerInfo.end(); i++) {
std::string parent = i->parentName;
Partition::Ptr part = partition(parent);
Layer layer;
layer.name = i->name;
layer.parent = i->parentName;
if (i->components == 1) {
part->addScalarLayer(layer);
} else if (i->components == 3) {
part->addVectorLayer(layer);
}
}
}
return true;
}
bool Field3DInputFile::readMetadata ( hid_t  metadata_id,
FieldBase::Ptr  field 
) const
private

Read metadata for this layer.

Todo:
Replace char* with std::string

Definition at line 821 of file Field3DFile.cpp.

References Hdf5Util::H5Base::id(), Msg::print(), Hdf5Util::readAttribute(), and Msg::SevWarning.

Referenced by open(), readLayer(), and readProxyLayer().

{
hsize_t num_attrs = H5Aget_num_attrs(metadata_id);
if (num_attrs > 0) {
for (hsize_t idx=0; idx < num_attrs ; ++idx) {
H5ScopedAopenIdx attrIdx(metadata_id, idx);
size_t len = H5Aget_name(attrIdx.id(), 0, NULL);
if (len > 0) {
char *name = new char[len+1];
if (H5Aget_name(attrIdx.id(), len+1, name) > 0) {
H5ScopedAopen attr(metadata_id, name, H5P_DEFAULT);
H5ScopedAget_space attrSpace(attr);
H5ScopedAget_type attrType(attr);
H5T_class_t typeClass = H5Tget_class(attrType);
if (typeClass == H5T_STRING) {
string value;
if (!readAttribute(metadata_id, name, value)) {
"Failed to read metadata " + string(name));
if (name) {
delete[] name;
}
continue;
}
field->metadata().setStrMetadata(name, value);
}
else {
if (H5Sget_simple_extent_ndims(attrSpace) != 1) {
Msg::print(Msg::SevWarning, "Bad attribute rank for attribute "
+ string(name));
if (name) {
delete[] name;
}
continue;
}
hsize_t dims[1];
H5Sget_simple_extent_dims(attrSpace, dims, NULL);
if (typeClass == H5T_INTEGER) {
if (dims[0] == 1){
int value;
if (!readAttribute(metadata_id, name, dims[0], value))
Msg::print(Msg::SevWarning, "Failed to read metadata "
+ string(name));
field->metadata().setIntMetadata(name, value);
}
else if (dims[0] == 3){
V3i value;
if (!readAttribute(metadata_id, name, dims[0], value.x))
Msg::print(Msg::SevWarning, "Failed to read metadata " +
string(name) );
field->metadata().setVecIntMetadata(name, value);
}
else {
"Attribute of size " +
boost::lexical_cast<std::string>(dims[0])
+ " is not valid for metadata");
}
}
else if (typeClass == H5T_FLOAT) {
if (dims[0] == 1){
float value;
if (!readAttribute(metadata_id, name, dims[0], value))
Msg::print(Msg::SevWarning, "Failed to read metadata " +
string(name) );
field->metadata().setFloatMetadata(name, value);
}
else if (dims[0] == 3){
V3f value;
if (!readAttribute(metadata_id, name, dims[0], value.x))
Msg::print(Msg::SevWarning, "Failed to read metadata "+
string(name) );
field->metadata().setVecFloatMetadata(name, value);
}
else {
Msg::print(Msg::SevWarning, "Attribute of size " +
boost::lexical_cast<std::string>(dims[0]) +
" is not valid for metadata");
}
}
else {
Msg::print(Msg::SevWarning, "Attribute '" + string(name) +
+ "' has unsupported data type for metadata");
}
}
}
if (name) {
delete[] name;
}
}
}
}
return true;
}
bool Field3DInputFile::readMetadata ( hid_t  metadata_id)
private

Read global metadata for this file.

Todo:
Replace char* with std::string

Definition at line 930 of file Field3DFile.cpp.

References Hdf5Util::H5Base::id(), Field3DFileBase::metadata(), Msg::print(), Hdf5Util::readAttribute(), FieldMetadata< CallBack_T >::setFloatMetadata(), FieldMetadata< CallBack_T >::setIntMetadata(), FieldMetadata< CallBack_T >::setStrMetadata(), FieldMetadata< CallBack_T >::setVecFloatMetadata(), FieldMetadata< CallBack_T >::setVecIntMetadata(), and Msg::SevWarning.

{
hsize_t num_attrs = H5Aget_num_attrs(metadata_id);
if (num_attrs > 0) {
for (hsize_t idx=0; idx < num_attrs ; ++idx) {
H5ScopedAopenIdx attrIdx(metadata_id, idx);
size_t len = H5Aget_name(attrIdx.id(), 0, NULL);
if (len > 0) {
char *name = new char[len+1];
if (H5Aget_name(attrIdx.id(), len+1, name) > 0) {
H5ScopedAopen attr(metadata_id, name, H5P_DEFAULT);
H5ScopedAget_space attrSpace(attr);
H5ScopedAget_type attrType(attr);
H5T_class_t typeClass = H5Tget_class(attrType);
if (typeClass == H5T_STRING) {
string value;
if (!readAttribute(metadata_id, name, value)) {
"Failed to read metadata " + string(name));
if (name) {
delete[] name;
}
continue;
}
metadata().setStrMetadata(name, value);
}
else {
if (H5Sget_simple_extent_ndims(attrSpace) != 1) {
Msg::print(Msg::SevWarning, "Bad attribute rank for attribute "
+ string(name));
if (name) {
delete[] name;
}
continue;
}
hsize_t dims[1];
H5Sget_simple_extent_dims(attrSpace, dims, NULL);
if (typeClass == H5T_INTEGER) {
if (dims[0] == 1){
int value;
if (!readAttribute(metadata_id, name, dims[0], value))
Msg::print(Msg::SevWarning, "Failed to read metadata "
+ string(name));
metadata().setIntMetadata(name, value);
}
else if (dims[0] == 3){
V3i value;
if (!readAttribute(metadata_id, name, dims[0], value.x))
Msg::print(Msg::SevWarning, "Failed to read metadata " +
string(name) );
metadata().setVecIntMetadata(name, value);
}
else {
"Attribute of size " +
boost::lexical_cast<std::string>(dims[0])
+ " is not valid for metadata");
}
}
else if (typeClass == H5T_FLOAT) {
if (dims[0] == 1){
float value;
if (!readAttribute(metadata_id, name, dims[0], value))
Msg::print(Msg::SevWarning, "Failed to read metadata " +
string(name) );
metadata().setFloatMetadata(name, value);
}
else if (dims[0] == 3){
V3f value;
if (!readAttribute(metadata_id, name, dims[0], value.x))
Msg::print(Msg::SevWarning, "Failed to read metadata "+
string(name) );
metadata().setVecFloatMetadata(name, value);
}
else {
Msg::print(Msg::SevWarning, "Attribute of size " +
boost::lexical_cast<std::string>(dims[0]) +
" is not valid for metadata");
}
}
else {
Msg::print(Msg::SevWarning, "Attribute '" + string(name) +
+ "' has unsupported data type for metadata");
}
}
}
if (name) {
delete[] name;
}
}
}
}
return true;
}

Member Data Documentation

std::string Field3DInputFile::m_filename
private

Filename, only to be set by open().

Definition at line 603 of file Field3DFile.h.

Referenced by open(), and readLayer().


The documentation for this class was generated from the following files: