Skip to content

Commit 4aa0c03

Browse files
Merge pull request #258 from ComputationalRadiationPhysics/dev
Release 1.6.0: SerialDataCollector Filename API
2 parents b8f9e33 + ba16465 commit 4aa0c03

15 files changed

Lines changed: 763 additions & 81 deletions

CHANGELOG.md

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,26 @@
11
Change Log for libSplash
22
================================================================
33

4+
Release 1.6.0
5+
-------------
6+
**Date:** 2016-10-28
7+
8+
`SerialDataCollector` file name interface change: this feature
9+
was accidentally not included in the `1.5.0` release.
10+
11+
**Interface Changes**
12+
13+
- `SerialDataCollector` file name interface changed #242
14+
15+
**Bug Fixes**
16+
17+
- compile with GCC 6.2 was broken: ambiguous `abs` #255
18+
19+
**Misc**
20+
21+
- tests: remove warning on deprecated CMake usage in 3.1+ #242
22+
23+
424
Release 1.5.0
525
-------------
626
**Date:** 2016-10-26

src/HandleMgr.cpp

Lines changed: 50 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/**
2-
* Copyright 2013 Felix Schmitt
2+
* Copyright 2013-2016 Felix Schmitt, Alexander Grund
33
*
44
* This file is part of libSplash.
55
*
@@ -27,17 +27,17 @@
2727
#include <hdf5.h>
2828

2929
#include "splash/core/HandleMgr.hpp"
30+
#include "splash/core/logging.hpp"
31+
#include "splash/core/DCHelper.hpp"
3032

3133
namespace splash
3234
{
3335

3436
HandleMgr::HandleMgr(uint32_t maxHandles, FileNameScheme fileNameScheme) :
3537
maxHandles(maxHandles),
36-
numHandles(0),
3738
mpiSize(1, 1, 1),
3839
fileNameScheme(fileNameScheme),
3940
fileFlags(0),
40-
singleFile(true),
4141
fileCreateCallback(NULL),
4242
fileCreateUserData(NULL),
4343
fileOpenCallback(NULL),
@@ -69,26 +69,53 @@ namespace splash
6969
return full_msg.str();
7070
}
7171

72+
void HandleMgr::setFileNameScheme(FileNameScheme fileNameScheme) throw (DCException)
73+
{
74+
if (this->fileNameScheme == fileNameScheme)
75+
return;
76+
if (!filename.empty())
77+
throw DCException(getExceptionString("setFileNameScheme",
78+
"Tried to change scheme while file(s) were still open", ""));
79+
this->fileNameScheme = fileNameScheme;
80+
}
81+
7282
void HandleMgr::open(Dimensions mpiSize, const std::string baseFilename,
7383
hid_t fileAccProperties, unsigned flags)
84+
throw (DCException)
7485
{
75-
this->numHandles = mpiSize.getScalarSize();
7686
this->mpiSize.set(mpiSize);
7787
this->filename = baseFilename;
7888
this->fileAccProperties = fileAccProperties;
7989
this->fileFlags = flags;
80-
this->singleFile = false;
90+
// Validation: For parallel files we normally append MPI rank or iteration number.
91+
// This is disabled by using FNS_FULLNAME
92+
// or when the filename already contains an h5-extension.
93+
if (fileNameScheme != FNS_FULLNAME && baseFilename.find(".h5") == baseFilename.length() - 3)
94+
{
95+
if (mpiSize.getScalarSize() > 1)
96+
{
97+
throw DCException(getExceptionString("open",
98+
"Passed full filename for parallel file operations",
99+
baseFilename.c_str()));
100+
} else
101+
{
102+
log_msg(1, "\n"
103+
"\tWarning: Passed full filename for parallel file operations: %s\n"
104+
"It is recommended to pass only the base name (no extension)"
105+
"and let the implementation choose a filename.\n", filename.c_str());
106+
}
107+
}
81108
}
82109

83110
void HandleMgr::open(const std::string fullFilename,
84111
hid_t fileAccProperties, unsigned flags)
112+
throw (DCException)
85113
{
86-
this->numHandles = 1;
114+
setFileNameScheme(FNS_FULLNAME);
87115
this->mpiSize.set(1, 1, 1);
88116
this->filename = fullFilename;
89117
this->fileAccProperties = fileAccProperties;
90118
this->fileFlags = flags;
91-
this->singleFile = true;
92119
}
93120

94121
uint32_t HandleMgr::indexFromPos(Dimensions& mpiPos)
@@ -125,7 +152,7 @@ namespace splash
125152
throw (DCException)
126153
{
127154
uint32_t index = 0;
128-
if (!singleFile)
155+
if (fileNameScheme != FNS_FULLNAME)
129156
index = indexFromPos(mpiPos);
130157

131158
HandleMap::iterator iter = handles.find(index);
@@ -150,28 +177,34 @@ namespace splash
150177
leastAccIndex.ctr = 0;
151178
}
152179

153-
std::stringstream filenameStream;
154-
filenameStream << filename;
155-
if (!singleFile)
180+
// Append prefix and extension if we don't have a full filename (extension)
181+
std::string fullFilename;
182+
if (fileNameScheme != FNS_FULLNAME && filename.find(".h5") != filename.length() - 3)
156183
{
184+
std::stringstream filenameStream;
185+
filenameStream << filename;
157186
if (fileNameScheme == FNS_MPI)
158187
{
159188
filenameStream << "_" << mpiPos[0] << "_" << mpiPos[1] <<
160189
"_" << mpiPos[2] << ".h5";
161-
} else
190+
} else if(fileNameScheme == FNS_ITERATIONS)
162191
filenameStream << "_" << mpiPos[0] << ".h5";
163-
}
192+
fullFilename = filenameStream.str();
193+
}else
194+
fullFilename = filename;
164195

165196
H5Handle newHandle = 0;
166197

167198
// serve requests to create files once as create and as read/write afterwards
168199
if ((fileFlags & H5F_ACC_TRUNC) && (createdFiles.find(index) == createdFiles.end()))
169200
{
170-
newHandle = H5Fcreate(filenameStream.str().c_str(), fileFlags,
201+
DCHelper::testFilename(fullFilename);
202+
203+
newHandle = H5Fcreate(fullFilename.c_str(), fileFlags,
171204
H5P_FILE_CREATE_DEFAULT, fileAccProperties);
172205
if (newHandle < 0)
173206
throw DCException(getExceptionString("get", "Failed to create file",
174-
filenameStream.str().c_str()));
207+
fullFilename.c_str()));
175208

176209
createdFiles.insert(index);
177210

@@ -184,10 +217,10 @@ namespace splash
184217
if (fileFlags & H5F_ACC_TRUNC)
185218
tmp_flags = H5F_ACC_RDWR;
186219

187-
newHandle = H5Fopen(filenameStream.str().c_str(), tmp_flags, fileAccProperties);
220+
newHandle = H5Fopen(fullFilename.c_str(), tmp_flags, fileAccProperties);
188221
if (newHandle < 0)
189222
throw DCException(getExceptionString("get", "Failed to open file",
190-
filenameStream.str().c_str()));
223+
fullFilename.c_str()));
191224

192225
if (fileOpenCallback)
193226
fileOpenCallback(newHandle, index, fileOpenUserData);
@@ -224,8 +257,6 @@ namespace splash
224257
leastAccIndex.ctr = 0;
225258
leastAccIndex.index = 0;
226259
mpiSize.set(1, 1, 1);
227-
numHandles = 0;
228-
singleFile = true;
229260

230261
// close all remaining handles
231262
HandleMap::const_iterator iter = handles.begin();

src/ParallelDataCollector.cpp

Lines changed: 7 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/**
2-
* Copyright 2013-2015 Felix Schmitt, Axel Huebl
2+
* Copyright 2013-2016 Felix Schmitt, Axel Huebl, Alexander Grund
33
*
44
* This file is part of libSplash.
55
*
@@ -67,14 +67,6 @@ namespace splash
6767
log_msg(3, "Raw Data Cache (File) = %llu KiB", (long long unsigned) (rawCacheSize / 1024));
6868
}
6969

70-
std::string ParallelDataCollector::getFullFilename(uint32_t id, std::string baseFilename)
71-
{
72-
std::stringstream serial_filename;
73-
serial_filename << baseFilename << "_" << id << ".h5";
74-
75-
return serial_filename.str();
76-
}
77-
7870
std::string ParallelDataCollector::getExceptionString(std::string func, std::string msg,
7971
const char *info)
8072
{
@@ -201,15 +193,16 @@ namespace splash
201193

202194
ParallelDataCollector::~ParallelDataCollector()
203195
{
196+
close();
204197
H5Pclose(fileAccProperties);
198+
finalize();
205199
}
206200

207201
void ParallelDataCollector::finalize()
208202
{
209-
log_msg(1, "finalizing data collector");
210-
211203
if (options.mpiComm != MPI_COMM_NULL)
212204
{
205+
log_msg(1, "finalizing data collector");
213206
MPI_Comm_free(&options.mpiComm);
214207
options.mpiComm = MPI_COMM_NULL;
215208
}
@@ -245,6 +238,9 @@ namespace splash
245238

246239
void ParallelDataCollector::close()
247240
{
241+
if (fileStatus == FST_CLOSED)
242+
return;
243+
248244
log_msg(1, "closing parallel data collector");
249245

250246
// close opened hdf5 file handles

src/SerialDataCollector.cpp

Lines changed: 29 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/**
2-
* Copyright 2013-2015 Felix Schmitt, Axel Huebl
2+
* Copyright 2013-2016 Felix Schmitt, Axel Huebl, Alexander Grund
33
*
44
* This file is part of libSplash.
55
*
@@ -35,7 +35,6 @@
3535
#include "splash/core/DCAttribute.hpp"
3636
#include "splash/core/DCDataSet.hpp"
3737
#include "splash/core/DCGroup.hpp"
38-
#include "splash/core/DCHelper.hpp"
3938
#include "splash/core/SDCHelper.hpp"
4039
#include "splash/core/logging.hpp"
4140
#include "splash/basetypes/basetypes.hpp"
@@ -70,8 +69,18 @@ namespace splash
7069
return (stat(filename.c_str(), &fileInfo) == 0);
7170
}
7271

73-
std::string SerialDataCollector::getFullFilename(const Dimensions mpiPos, std::string baseFilename) const
72+
std::string SerialDataCollector::getFullFilename(const Dimensions mpiPos, std::string baseFilename,
73+
bool isFullNameAllowed) const throw (DCException)
7474
{
75+
// Check for existing extension
76+
if (baseFilename.find(".h5") == baseFilename.length() - 3)
77+
{
78+
if (isFullNameAllowed)
79+
return baseFilename;
80+
else
81+
throw DCException("Full filename is not allowed!");
82+
}
83+
7584
std::stringstream serial_filename;
7685
serial_filename << baseFilename << "_" << mpiPos[0] << "_" << mpiPos[1] <<
7786
"_" << mpiPos[2] << ".h5";
@@ -97,7 +106,7 @@ namespace splash
97106
*******************************************************************************/
98107

99108
SerialDataCollector::SerialDataCollector(uint32_t maxFileHandles) :
100-
handles(maxFileHandles, HandleMgr::FNS_MPI),
109+
handles(maxFileHandles, HandleMgr::FNS_FULLNAME),
101110
fileStatus(FST_CLOSED),
102111
maxID(-1),
103112
mpiTopology(1, 1, 1)
@@ -113,7 +122,7 @@ namespace splash
113122
"failed to initialize/open HDF5 library"));
114123

115124
#ifndef SPLASH_VERBOSE_HDF5
116-
// surpress automatic output of HDF5 exception messages
125+
// Suppress automatic output of HDF5 exception messages
117126
if (H5Eset_auto2(H5E_DEFAULT, NULL, NULL) < 0)
118127
throw DCException(getExceptionString("SerialDataCollector",
119128
"failed to disable error printing"));
@@ -125,6 +134,7 @@ namespace splash
125134

126135
SerialDataCollector::~SerialDataCollector()
127136
{
137+
close();
128138
}
129139

130140
void SerialDataCollector::open(const char* filename, FileCreationAttr &attr)
@@ -157,16 +167,19 @@ namespace splash
157167

158168
void SerialDataCollector::close()
159169
{
170+
if (fileStatus == FST_CLOSED)
171+
return;
172+
160173
log_msg(1, "closing serial data collector");
161174

162-
if (fileStatus == FST_CREATING || fileStatus == FST_WRITING)
175+
if ((fileStatus == FST_CREATING || fileStatus == FST_WRITING) &&
176+
maxID >= 0)
163177
{
164-
DCGroup group;
165-
group.open(handles.get(0), SDC_GROUP_HEADER);
166-
167178
// write number of iterations
168179
try
169180
{
181+
DCGroup group;
182+
group.open(handles.get(0), SDC_GROUP_HEADER);
170183
ColTypeInt32 ctInt32;
171184
DCAttribute::writeAttribute(SDC_ATTR_MAX_ID, ctInt32.getDataType(),
172185
group.getHandle(), &maxID);
@@ -759,9 +772,8 @@ namespace splash
759772
{
760773
this->fileStatus = FST_CREATING;
761774

762-
// appends the mpiPosition to the filename (e.g. myfile_0_1_0.h5)
763-
std::string full_filename = getFullFilename(attr.mpiPosition, filename);
764-
DCHelper::testFilename(full_filename);
775+
std::string full_filename = getFullFilename(attr.mpiPosition, filename,
776+
attr.mpiSize.getScalarSize() == 1);
765777

766778
this->enableCompression = attr.enableCompression;
767779

@@ -792,11 +804,8 @@ namespace splash
792804
{
793805
fileStatus = FST_WRITING;
794806

795-
std::string full_filename = filename;
796-
if (full_filename.find(".h5") == std::string::npos)
797-
full_filename = getFullFilename(attr.mpiPosition, filename);
798-
799-
DCHelper::testFilename(full_filename);
807+
std::string full_filename = getFullFilename(attr.mpiPosition, filename,
808+
attr.mpiSize.getScalarSize() == 1);
800809

801810
this->enableCompression = attr.enableCompression;
802811

@@ -818,9 +827,7 @@ namespace splash
818827
this->fileStatus = FST_MERGING;
819828

820829
// open reference file to get mpi information
821-
std::string full_filename = getFullFilename(Dimensions(0, 0, 0), filename);
822-
823-
DCHelper::testFilename(full_filename);
830+
std::string full_filename = getFullFilename(Dimensions(0, 0, 0), filename, true);
824831

825832
if (!fileExists(full_filename))
826833
{
@@ -834,6 +841,7 @@ namespace splash
834841
// no compression for in-memory datasets
835842
this->enableCompression = false;
836843

844+
handles.setFileNameScheme(HandleMgr::FNS_MPI);
837845
handles.open(mpiTopology, filename, fileAccProperties, H5F_ACC_RDONLY);
838846
}
839847

@@ -842,11 +850,7 @@ namespace splash
842850
{
843851
this->fileStatus = FST_READING;
844852

845-
std::string full_filename = filename;
846-
if (full_filename.find(".h5") == std::string::npos)
847-
full_filename = getFullFilename(attr.mpiPosition, filename);
848-
849-
DCHelper::testFilename(full_filename);
853+
std::string full_filename = getFullFilename(attr.mpiPosition, filename, true);
850854

851855
if (!fileExists(full_filename))
852856
{

src/include/splash/ParallelDataCollector.hpp

Lines changed: 0 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -54,16 +54,6 @@ namespace splash
5454
*/
5555
void setFileAccessParams(hid_t& fileAccProperties);
5656

57-
/**
58-
* Constructs a filename from a base filename and the current id
59-
* such as baseFilename+id+.h5
60-
*
61-
* @param id Iteration ID.
62-
* @param baseFilename Base filename for the new file.
63-
* @return newly Constructed filename including file extension.
64-
*/
65-
static std::string getFullFilename(uint32_t id, std::string baseFilename);
66-
6757
/**
6858
* Internal function for formatting exception messages.
6959
*

0 commit comments

Comments
 (0)