Gitlab.kitware.com will be offline between 8am and midnight (EST/UTC-0500) on Saturday, December 15th.

Commit 2db94e49 authored by Burlen Loring's avatar Burlen Loring

Merge branch 'adios_bp_fixes' into 'master'

* Fixes an issues with BP read method
* Add support for CTest
* Add regression test for ADIOS FLEXPATH and BP methods
* Fix version detection regex, it did not work with tags
* Cleanup warnings reported by Apple Clang
* Fix missing include in Python wrapping
* Hide static overloads from SWIG
* Fix CMake warnings about CMP00053

See merge request !48
parents ea860e28 3c700018
set(SENSEI_DATA_ROOT "" CACHE PATH "Path to SENSEI test data")
set(BUILD_TESTING OFF CACHE BOOL "Enable tests")
if (BUILD_TESTING)
enable_testing()
include(CTest)
endif()
# sensei_add_test(name
# EXEC_NAME -- optional, name of the copiled test
# SOURCES -- optional, source files to comile
# LIBS -- optional, libraries to link to the compiled test
# COMMAND -- required, test command
# FEATURES -- optional, boolean condition decribing feature dependencies
# REQ_SENSEI_DATA -- flag whose presence indicates the test needs the data repo
# )
function (sensei_add_test T_NAME)
set(opt_args REQ_SENSEI_DATA)
set(val_args EXEC_NAME)
set(array_args SOURCES LIBS COMMAND FEATURES)
cmake_parse_arguments(T "${opt_args}" "${val_args}" "${array_args}" ${ARGN})
set(TEST_ENABLED ON)
if (NOT DEFINED T_FEATURES)
set(TEST_ENABLED ON)
else()
foreach(feature ${T_FEATURES})
if (NOT feature)
set(TEST_ENABLED OFF)
endif()
endforeach()
endif()
if (TEST_ENABLED)
if (T_SOURCES)
set(EXEC_NAME ${T_NAME})
if (T_EXEC_NAME)
set(EXEC_NAME ${T_EXEC_NAME})
endif()
add_executable(${EXEC_NAME} ${T_SOURCES})
if (T_LIBS)
target_link_libraries(${EXEC_NAME} ${T_LIBS})
endif()
endif()
if ((T_REQ_SENSEI_DATA AND SENSEI_DATA_ROOT) OR NOT T_REQ_SENSEI_DATA)
add_test(NAME ${T_NAME} COMMAND ${T_COMMAND}
WORKING_DIRECTORY ${CMAKE_RUNTIME_OUTPUT_DIRECTORY})
set_tests_properties(${T_NAME}
PROPERTIES FAIL_REGULAR_EXPRESSION "[Ee][Rr][Rr][Oo][Rr]")
endif()
endif()
endfunction()
......@@ -10,18 +10,15 @@ if(NOT tmp)
endif()
set(SENSEI_VERSION ${tmp} CACHE STRING "SENSEI version")
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)\\-[0-9]+\\-([0-9a-zA-Z]+)"
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)(.*$)"
"\\1" SENSEI_VERSION_MAJOR ${SENSEI_VERSION})
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)\\-[0-9]+\\-([0-9a-zA-Z]+)"
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)(.*$)"
"\\2" SENSEI_VERSION_MINOR ${SENSEI_VERSION})
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)\\-[0-9]+\\-([0-9a-zA-Z]+)"
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)(.*$)"
"\\3" SENSEI_VERSION_PATCH ${SENSEI_VERSION})
string(REGEX REPLACE "^v([0-9]+)\\.([0-9]+)\\.([0-9]+)\\-[0-9]+\\-([0-9a-zA-Z]+)"
"\\4" SENSEI_VERSION_DEVEL ${SENSEI_VERSION})
message(STATUS "SENSEI_VERSION_MAJOR=${SENSEI_VERSION_MAJOR}")
message(STATUS "SENSEI_VERSION_MINOR=${SENSEI_VERSION_MINOR}")
message(STATUS "SENSEI_VERSION_PATCH=${SENSEI_VERSION_PATCH}")
cmake_minimum_required(VERSION 3.0)
cmake_minimum_required(VERSION 3.1)
project(sensei)
include(CMakeDependentOption)
......@@ -15,6 +15,7 @@ include(catalyst)
include(python)
include(version)
include(config)
include(testing)
add_subdirectory(utils)
add_subdirectory(sensei)
......
set(CTEST_PROJECT_NAME "SENSEI")
set(CTEST_NIGHTLY_START_TIME "18:00:00 EDT")
set(CTEST_DROP_METHOD "http")
set(CTEST_DROP_SITE "cdash.hpcvis.com")
set(CTEST_DROP_LOCATION "/submit.php?project=SENSEI")
set(CTEST_DROP_SITE_CDASH TRUE)
......@@ -68,19 +68,12 @@ int main(int argc, char **argv)
timer::SetLogging(log || shortlog);
timer::SetTrackSummariesOverTime(shortlog);
std::map<std::string, ADIOS_READ_METHOD> readmethods;
readmethods["bp"] = ADIOS_READ_METHOD_BP;
readmethods["bp_aggregate"] = ADIOS_READ_METHOD_BP_AGGREGATE;
readmethods["dataspaces"] = ADIOS_READ_METHOD_DATASPACES;
readmethods["dimes"] = ADIOS_READ_METHOD_DIMES;
readmethods["flexpath"] = ADIOS_READ_METHOD_FLEXPATH;
SENSEI_STATUS("Opening: \"" << input.c_str() << "\" using method \""
<< readmethod.c_str() << "\"")
// open the ADIOS stream using the ADIOS adaptor
DataAdaptorPtr dataAdaptor = DataAdaptorPtr::New();
if (dataAdaptor->Open(comm, readmethods[readmethod], input))
if (dataAdaptor->Open(comm, readmethod, input))
{
SENSEI_ERROR("Failed to open \"" << input << "\"")
MPI_Abort(comm, 1);
......
......@@ -8,7 +8,8 @@ if(ENABLE_SENSEI)
endif()
add_library(util STATIC src/format.cc)
target_include_directories(util PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/include)
target_include_directories(util SYSTEM PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}/include)
add_executable(oscillator ${sources})
target_link_libraries(oscillator ${libs})
......@@ -2,6 +2,7 @@ if (ENABLE_PYTHON)
depend_swig(senseiPython.i senseiPython.dep)
wrap_swig(senseiPython.i senseiPython.cxx senseiPython.dep)
include_directories(SYSTEM ${PYTHON_INCLUDE_PATH} ${NUMPY_INCLUDE_DIR})
include_directories(${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_BINARY_DIR}
${CMAKE_CURRENT_BINARY_DIR})
......
......@@ -38,6 +38,8 @@ VTK_SWIG_INTEROP(vtkInformation)
methods is causing the problem */
%ignore sensei::DataAdaptor::SetDataTime(vtkInformation *,double);
%ignore sensei::DataAdaptor::SetDataTimeStep(vtkInformation *,int);
%ignore sensei::DataAdaptor::GetDataTime(vtkInformation *);
%ignore sensei::DataAdaptor::GetDataTimeStep(vtkInformation *);
VTK_DERIVED(DataAdaptor)
VTK_DERIVED(AnalysisAdaptor)
......
......@@ -22,43 +22,19 @@ namespace sensei
struct ADIOSDataAdaptor::InternalsType
{
InternalsType() : Comm(MPI_COMM_WORLD), File(nullptr),
Mesh(nullptr), StaticMesh(0), StructureOnly(0),
Method(ADIOS_READ_METHOD_BP)
InternalsType() : Comm(MPI_COMM_WORLD), Stream(),
Mesh(nullptr), StaticMesh(0), StructureOnly(0)
{}
bool MethodIsFileBased(ADIOS_READ_METHOD method);
bool MethodIsFileBased()
{ return this->MethodIsFileBased(this->Method); }
MPI_Comm Comm;
ADIOS_FILE *File;
senseiADIOS::InputStream Stream;
senseiADIOS::DataObjectSchema Schema;
vtkDataObjectPtr Mesh;
ArrayMapType ArrayNames;
int StaticMesh;
int StructureOnly;
ADIOS_READ_METHOD Method;
};
bool ADIOSDataAdaptor::InternalsType::MethodIsFileBased(ADIOS_READ_METHOD method)
{
switch(method)
{
case ADIOS_READ_METHOD_BP:
case ADIOS_READ_METHOD_BP_AGGREGATE:
return true;
case ADIOS_READ_METHOD_DATASPACES:
case ADIOS_READ_METHOD_DIMES:
case ADIOS_READ_METHOD_FLEXPATH:
case ADIOS_READ_METHOD_ICEE:
return false;
}
SENSEI_ERROR("unknown read method " << method)
return false;
}
//----------------------------------------------------------------------------
senseiNewMacro(ADIOSDataAdaptor);
......@@ -83,38 +59,46 @@ void ADIOSDataAdaptor::EnableDynamicMesh(int val)
//----------------------------------------------------------------------------
int ADIOSDataAdaptor::Open(MPI_Comm comm,
ADIOS_READ_METHOD method, const std::string& filename)
const std::string &method, const std::string& filename)
{
timer::MarkEvent mark("ADIOSDataAdaptor::Open");
// initialize adios
adios_read_init_method(method, comm, "verbose=2");
// open the file
ADIOS_FILE *fp = adios_read_open(filename.c_str(), method, comm,
this->Internals->MethodIsFileBased(method) ? ADIOS_LOCKMODE_ALL :
ADIOS_LOCKMODE_CURRENT, -1.0f);
if (!fp)
size_t n = method.size();
std::string lcase_method(n, ' ');
for (size_t i = 0; i < n; ++i)
lcase_method[i] = tolower(method[i]);
std::map<std::string, ADIOS_READ_METHOD> readMethods;
readMethods["bp"] = ADIOS_READ_METHOD_BP;
readMethods["bp_aggregate"] = ADIOS_READ_METHOD_BP_AGGREGATE;
readMethods["dataspaces"] = ADIOS_READ_METHOD_DATASPACES;
readMethods["dimes"] = ADIOS_READ_METHOD_DIMES;
readMethods["flexpath"] = ADIOS_READ_METHOD_FLEXPATH;
std::map<std::string, ADIOS_READ_METHOD>::iterator it =
readMethods.find(lcase_method);
if (it == readMethods.end())
{
SENSEI_ERROR("failed to open " << filename)
SENSEI_ERROR("Unsupported read method requested \"" << method << "\"")
return -1;
}
// verify that it is one of ours
if (this->Internals->Schema.CanRead(comm, fp))
return this->Open(comm, it->second, filename);
}
//----------------------------------------------------------------------------
int ADIOSDataAdaptor::Open(MPI_Comm comm,
ADIOS_READ_METHOD method, const std::string& fileName)
{
timer::MarkEvent mark("ADIOSDataAdaptor::Open");
this->Internals->Comm = comm;
if (this->Internals->Stream.Open(comm, method, fileName))
{
adios_read_close(fp);
SENSEI_ERROR("Failed to open \"" << filename << "\". Stream "
"was not written in the SENSEI ADIOS schema format")
SENSEI_ERROR("Failed to open \"" << fileName << "\"")
return -1;
}
//
this->Internals->Comm = comm;
this->Internals->File = fp;
this->Internals->Method = method;
// initialize the time step
if (this->UpdateTimeStep())
return -1;
......@@ -131,12 +115,7 @@ int ADIOSDataAdaptor::Close()
this->Internals->ArrayNames[vtkDataObject::POINT].clear();
this->Internals->ArrayNames[vtkDataObject::CELL].clear();
if (this->Internals->File)
{
adios_read_close(this->Internals->File);
adios_read_finalize_method(this->Internals->Method);
this->Internals->File = nullptr;
}
this->Internals->Stream.Close();
return 0;
}
......@@ -146,11 +125,8 @@ int ADIOSDataAdaptor::Advance()
{
timer::MarkEvent mark("ADIOSDataAdaptor::Advance");
adios_release_step(this->Internals->File);
if (adios_advance_step(this->Internals->File, 0,
this->Internals->MethodIsFileBased() ? 0.0f : -1.0f))
return 1;
if (this->Internals->Stream.AdvanceTimeStep())
return -1;
if (this->UpdateTimeStep())
return -1;
......@@ -168,7 +144,7 @@ int ADIOSDataAdaptor::UpdateTimeStep()
double time = 0.0;
if (this->Internals->Schema.ReadTimeStep(this->Internals->Comm,
this->Internals->File, timeStep, time))
this->Internals->Stream, timeStep, time))
{
SENSEI_ERROR("Failed to update time step")
return -1;
......@@ -195,7 +171,7 @@ vtkDataObject* ADIOSDataAdaptor::GetMesh(bool structure_only)
// get the mesh at the current time step
vtkDataObject *mesh = nullptr;
if (this->Internals->Schema.ReadMesh(this->Internals->Comm,
this->Internals->File, structure_only, mesh))
this->Internals->Stream, structure_only, mesh))
{
SENSEI_ERROR("Failed to read mesh")
return nullptr;
......@@ -209,7 +185,7 @@ vtkDataObject* ADIOSDataAdaptor::GetMesh(bool structure_only)
// point data arrays
std::set<std::string> point_arrays;
if (this->Internals->Schema.ReadArrayNames(this->Internals->Comm,
this->Internals->File, mesh, vtkDataObject::POINT, point_arrays))
this->Internals->Stream, mesh, vtkDataObject::POINT, point_arrays))
{
SENSEI_ERROR("Failed to read point associated array names")
return nullptr;
......@@ -220,7 +196,7 @@ vtkDataObject* ADIOSDataAdaptor::GetMesh(bool structure_only)
// cell data arrays
std::set<std::string> cell_arrays;
if (this->Internals->Schema.ReadArrayNames(this->Internals->Comm,
this->Internals->File, mesh, vtkDataObject::CELL, cell_arrays))
this->Internals->Stream, mesh, vtkDataObject::CELL, cell_arrays))
{
SENSEI_ERROR("Failed to read cell associated array names")
return nullptr;
......@@ -267,7 +243,7 @@ bool ADIOSDataAdaptor::AddArray(vtkDataObject* mesh, int association,
}
if (this->Internals->Schema.ReadArray(this->Internals->Comm,
this->Internals->File, mesh, association, name))
this->Internals->Stream, mesh, association, name))
{
SENSEI_ERROR("Failed to read "
<< (association == vtkDataObject::POINT ? "point" : "cell")
......
......@@ -20,7 +20,9 @@ public:
senseiTypeMacro(ADIOSDataAdaptor, ADIOSDataAdaptor);
void PrintSelf(ostream& os, vtkIndent indent) override;
int Open(MPI_Comm comm, const std::string &method, const std::string& filename);
int Open(MPI_Comm comm, ADIOS_READ_METHOD method, const std::string& filename);
int Close();
// Set the mesh type to static or dynamic. A static mesh does not
......
This diff is collapsed.
......@@ -5,6 +5,7 @@ class vtkDataSet;
class vtkDataObject;
typedef struct _ADIOS_FILE ADIOS_FILE;
#include <adios_read.h>
#include <vtkDataObject.h>
#include <mpi.h>
#include <set>
......@@ -13,6 +14,8 @@ typedef struct _ADIOS_FILE ADIOS_FILE;
namespace senseiADIOS
{
struct InputStream;
/// Base class for representing VTK data in ADIOS.
// the 3 operations that need to be done to send data to ADIOS are:
//
......@@ -45,8 +48,8 @@ public:
virtual int Write(int64_t fh, unsigned int id, vtkDataSet *ds);
// Read data from ADIOS
virtual int Read(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *&dobj);
virtual int Read(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id, vtkDataSet *&ds);
virtual int Read(MPI_Comm comm, InputStream &iStream, vtkDataObject *&dobj);
virtual int Read(MPI_Comm comm, InputStream &iStream, unsigned int id, vtkDataSet *&ds);
};
......@@ -74,32 +77,32 @@ public:
int Write(MPI_Comm comm, int64_t fh, vtkDataObject *dobj) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *&dobj) override;
int Read(MPI_Comm comm, InputStream &iStream, vtkDataObject *&dobj) override;
// verifies that the file is ours
int CanRead(MPI_Comm comm, ADIOS_FILE *fp);
int CanRead(MPI_Comm comm, InputStream &iStream);
// creates the mesh matching what is on disk(or stream), indluding a domain
// decomposition, but does not read data arrays. If structure_only is true
// then points and cells are not read from disk.
int ReadMesh(MPI_Comm comm, ADIOS_FILE *fp, bool structure_only,
int ReadMesh(MPI_Comm comm, InputStream &iStream, bool structure_only,
vtkDataObject *&dobj);
// discover names of data arrays on disk(or stream)
int ReadArrayNames(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *dobj,
int ReadArrayNames(MPI_Comm comm, InputStream &iStream, vtkDataObject *dobj,
int association, std::set<std::string> &array_names);
// read a single array from disk(or stream), store it into the mesh
int ReadArray(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *dobj,
int ReadArray(MPI_Comm comm, InputStream &iStream, vtkDataObject *dobj,
int association, const std::string &name);
// returns the current time and time step
int ReadTimeStep(MPI_Comm comm, ADIOS_FILE *fp,
int ReadTimeStep(MPI_Comm comm, InputStream &iStream,
unsigned long &time_step, double &time);
private:
// create data object
int InitializeDataObject(MPI_Comm comm, ADIOS_FILE *fp,
int InitializeDataObject(MPI_Comm comm, InputStream &iStream,
vtkDataObject *&dobj);
struct InternalsType;
......@@ -126,26 +129,26 @@ public:
int Write(MPI_Comm comm, int64_t fh, vtkDataObject *dobj) override;
int Write(int64_t fh, unsigned int id, vtkDataSet *ds) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *&dobj) override;
int Read(MPI_Comm comm, InputStream &iStream, vtkDataObject *&dobj) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int Read(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *&ds) override;
// creates the mesh matching what is on disk(or stream), indluding a domain
// decomposition, but does not read data arrays. If structure_only is true
// then points and cells are not read from disk.
int ReadMesh(MPI_Comm comm, ADIOS_FILE *fp, bool structure_only,
int ReadMesh(MPI_Comm comm, InputStream &iStream, bool structure_only,
vtkDataObject *&dobj);
int ReadMesh(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int ReadMesh(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *&ds, bool structure_only);
// discover names of data arrays on disk(or stream)
int ReadArrayNames(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *dobj,
int ReadArrayNames(MPI_Comm comm, InputStream &iStream, vtkDataObject *dobj,
int association, std::set<std::string> &array_names);
// read a single array from disk(or stream), store it into the mesh
int ReadArray(MPI_Comm comm, ADIOS_FILE *fp, vtkDataObject *dobj,
int ReadArray(MPI_Comm comm, InputStream &iStream, vtkDataObject *dobj,
int association, const std::string &name);
// define the local domain decomposition by a start data object id
......@@ -177,7 +180,7 @@ public:
int Write(int64_t fh, unsigned int id, vtkDataSet *ds) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int Read(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *&ds) override;
};
......@@ -204,21 +207,21 @@ public:
int Write(int64_t fh, unsigned int id, vtkDataSet *ds) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int Read(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *&ds) override;
// discover names of data arrays
int ReadArrayNames(MPI_Comm comm, ADIOS_FILE *fp,
int ReadArrayNames(MPI_Comm comm, InputStream &iStream,
vtkDataObject *dobj, std::set<std::string> &array_names);
int ReadArrayNames(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int ReadArrayNames(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *ds, std::set<std::string> &array_names);
// read a single array and store it into the mesh
int ReadArray(MPI_Comm comm, ADIOS_FILE *fp,
int ReadArray(MPI_Comm comm, InputStream &iStream,
const std::string &array_name, vtkDataObject *dobj);
int ReadArray(MPI_Comm comm, ADIOS_FILE *fp,
int ReadArray(MPI_Comm comm, InputStream &iStream,
const std::string &array_name, unsigned int id, vtkDataSet *ds);
private:
......@@ -248,7 +251,7 @@ public:
int Write(int64_t fh, unsigned int id, vtkDataSet *ds) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int Read(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *&ds) override;
// get length of arrays
......@@ -279,7 +282,7 @@ public:
int Write(int64_t fh, unsigned int id, vtkDataSet *ds) override;
int Read(MPI_Comm comm, ADIOS_FILE *fp, unsigned int id,
int Read(MPI_Comm comm, InputStream &iStream, unsigned int id,
vtkDataSet *&ds) override;
// get length of arrays
......@@ -292,6 +295,28 @@ public:
static unsigned long GetNumberOfPoints(vtkDataSet *ds);
};
/// High level operations on an ADIOS file/stream
struct InputStream
{
InputStream() : File(nullptr),
ReadMethod(static_cast<ADIOS_READ_METHOD>(-1)) {}
InputStream(ADIOS_FILE *file, ADIOS_READ_METHOD method)
: File(file), ReadMethod(method) {}
int Open(MPI_Comm comm, ADIOS_READ_METHOD method,
const std::string &fileName);
int AdvanceTimeStep();
int Close();
ADIOS_FILE *File;
ADIOS_READ_METHOD ReadMethod;
};
}
#endif
......@@ -56,4 +56,5 @@ if (ENABLE_SENSEI)
install(EXPORT sensei DESTINATION lib/cmake
EXPORT_LINK_INTERFACE_LIBRARIES)
add_subdirectory(testing)
endif()
if (BUILD_TESTING)
sensei_add_test(test_adios_flexpath
COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/test_adios.sh 2
${CMAKE_CURRENT_SOURCE_DIR} test_adios_flexpath.bp
FLEXPATH FLEXPATH 2
FEATURES ${ENABLE_PYTHON} ${ENABLE_ADIOS})
sensei_add_test(test_adios_mpi_bp
COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/test_adios.sh 2
${CMAKE_CURRENT_SOURCE_DIR} test_adios_mpi_bp.bp
MPI BP 2
FEATURES ${ENABLE_PYTHON} ${ENABLE_ADIOS})
endif()
#!/usr/bin/env bash
if [[ $# < 6 ]]
then
echo "test_adios.sh [nproc] [src dir] [file] [write method] [read method] [nits]"
exit 1
fi
nproc=$1
srcdir=$2
file=$3
write_method=$4
read_method=$5
nits=$6
delay=1s
trap 'echo $BASH_COMMAND' DEBUG
rm -f ${file}
mpiexec -np ${nproc} python ${srcdir}/test_adios_write.py ${file} ${write_method} ${nits} &
write_pid=$!
if [[ "${read_method}" == "BP" ]]
then
echo "waiting for writer(${write_pid}) to complete"
wait ${write_pid}
elif [[ "${read_method}" == "FLEXPATH" ]]
then
echo "waiting for writer to start ${delay}"
while [[ True ]]
do
if [[ -e "${file}_writer_info.txt" ]]
then
break
else
sleep ${delay}
fi
done
fi
mpiexec -np ${nproc} python ${srcdir}/test_adios_read.py ${file} ${read_method}
exit 0
from mpi4py import *
from multiprocessing import Process,Lock,Value
from sensei import VTKDataAdaptor,ADIOSDataAdaptor,ADIOSAnalysisAdaptor
import sys,os
import numpy as np
import vtk, vtk.util.numpy_support as vtknp
from time import sleep
comm = MPI.COMM_WORLD
rank = comm.Get_rank()
n_ranks = comm.Get_size()
def error_message(msg):
sys.stderr.write('ERROR[%d] : %s\n'%(rank, msg))
def status_message(msg, io_rank=0):
if rank == io_rank:
sys.stderr.write('STATUS[%d] : %s\n'%(rank, msg))
def check_array(array):
# checks that array[i] == i
test_array = vtknp.vtk_to_numpy(array)
n_vals = len(test_array)
base_array = np.empty(n_vals, dtype=test_array.dtype)
i = 0
while i < n_vals:
base_array[i] = i
i += 1
ids = np.where(base_array != test_array)[0]
if len(ids):
error_message('wrong values at %s'%(str(ids)))
return -1
return 0
def read_data(file_name, method):
# initialize the data adaptor
status_message('initializing ADIOSDataAdaptor %s %s'%(file_name,method))
da = ADIOSDataAdaptor.New()
da.Open(MPI.COMM_WORLD, method, file_name)
# process all time steps
n_steps = 0
retval = 0
while True:
# get the time info
t = da.GetDataTime()
it = da.GetDataTimeStep()
status_message('received step %d time %0.1f'%(it, t))
# get a VTK dataset with all the arrays
ds = da.GetMesh(False)
# request each array
assocs = {vtk.VTK_POINT_DATA:'point', vtk.VTK_CELL_DATA:'cell'}
for assoc,assoc_name in assocs.iteritems():
n_arrays = da.GetNumberOfArrays(assoc)
i = 0
while i < n_arrays:
array_name = da.GetArrayName(assoc, i)
da.AddArray(ds, assoc, array_name)
i += 1
# this often will cause segv's if the dataset has been
# improperly constructed, thus serves as a good check
str_rep = str(ds)
# check the arrays have the expected data
it = ds.NewIterator()
while not it.IsDoneWithTraversal():
bds = it.GetCurrentDataObject()
idx = it.GetCurrentFlatIndex()
for assoc,assoc_name in assocs.iteritems():
n_arrays = da.GetNumberOfArrays(assoc)
status_message('checking %d %s data arrays ' \
'in block %d %s'%(n_arrays,assoc_name,idx,bds.GetClassName()), \
rank)
j = 0
while j < n_arrays:
array = bds.GetPointData().GetArray(j) \
if assoc == vtk.VTK_POINT_DATA else \
bds.GetCellData().GetArray(j)
if (check_array(array)):
error_message('Test failed on array %d "%s"'%( \
j, array.GetName()))
retval = -1
j += 1
it.GoToNextItem()
n_steps += 1
if (da.Advance()):
break
# close down the stream
da.Close()
status_message('closed stream after receiving %d steps'%(n_steps))
return retval
if __name__ == '__main__':
# process command line
file_name = sys.argv[1]
method = sys.argv[2]
# write data
ierr = read_data(file_name, method)
if ierr:
error_message('read failed')
# return the error code
sys.exit(ierr)
from mpi4py import *
from sensei import VTKDataAdaptor,ADIOSDataAdaptor,ADIOSAnalysisAdaptor
import sys,os
import numpy as np
import vtk, vtk.util.numpy_support as vtknp
from time import sleep
from random import seed,random
comm = MPI.COMM_WORLD
rank = comm.Get_rank()
n_ranks = comm.Get_size()
def error_message(msg):
sys.stderr.write('ERROR[%d] : %s\n'%(rank, msg))
def status_message(msg, io_rank=0):
if rank == io_rank:
sys.stderr.write('STATUS[%d] : %s\n'%(rank, msg))
def get_data_array(name, size, dtype):
a = np.empty(size, dtype=dtype)
i = 0