diff --git a/examples/heatTransfer/CMakeLists.txt b/examples/heatTransfer/CMakeLists.txt
index f6c932be42dd7223d5e08f12a3eb710d4947a433..52f9cab1af4d6a08dddce9d94edadcaebeda094d 100644
--- a/examples/heatTransfer/CMakeLists.txt
+++ b/examples/heatTransfer/CMakeLists.txt
@@ -4,4 +4,5 @@
 #------------------------------------------------------------------------------#
 
 add_subdirectory(write)
-add_subdirectory(read)
\ No newline at end of file
+add_subdirectory(read)
+add_subdirectory(read_fileonly)
diff --git a/examples/heatTransfer/ReadMe.md b/examples/heatTransfer/ReadMe.md
index 639eed4e70759be5ae7ed0e533c20e3b00da4232..eabafd502f8e11b83226bb5f1c9f97acaef7ebf4 100644
--- a/examples/heatTransfer/ReadMe.md
+++ b/examples/heatTransfer/ReadMe.md
@@ -1,15 +1,21 @@
 examples/heatTransfer
 
 Test that solves a 2D Poisson equation for temperature in homogeneous media
-using finite differences. This examples shows a straight-forward way to hook an
-application to the ADIOS2 library for its IO.
+using finite differences. This examples shows a straight-forward way to hook 
+an application to the ADIOS2 library for its IO.
 
 
-1. read: illustrates an experimental Read API, uses adios1 underneath  
+1. read: illustrates the Read API that allows running the reader either as
 
-2. write: illustrates the Write API, resulting binaries under build/bin require arguments  
+    * post-mortem to read all output steps
+    * in situ to read step by step as the writer outputs them
+
+2. write: illustrates the Write API as well as has implementations of other IO libraries
   
-    * adios1    
-    * adios2
+    * adios 1.x    
     * hdf5
-    * phdf5
\ No newline at end of file
+    * phdf5
+
+3. read_fileonly: illustrates reading all output steps at once (a single read 
+   statement) into a single contiguous memory block. This approach only works 
+   for post-mortem processing. 
diff --git a/examples/heatTransfer/heat.xml b/examples/heatTransfer/heat.xml
new file mode 100644
index 0000000000000000000000000000000000000000..56cd16dbba573016586f54b8cac104013d449255
--- /dev/null
+++ b/examples/heatTransfer/heat.xml
@@ -0,0 +1,84 @@
+<?xml version="1.0"?>
+<!-- Config XML file fo the  
+     - heatTransfer_write_adios2 
+     - heatTransfer_read
+     executables in build/bin -->
+
+<adios-config>
+
+    <!--====================================
+           Configuration for the Writer 
+        ====================================-->
+
+    <io name="writer">
+        <engine type="BPFileWriter">
+            
+            <!-- for vectorized memory operations, make sure your system 
+                 enables threads--> 
+            <parameter key="Threads" value="2"/>
+
+            <!-- Microseconds (default), Milliseconds, Seconds, 
+                 Minutes, Hours -->
+            <parameter key="ProfileUnits" value="Microseconds"/>
+
+            <!-- XXKb, XXMb, or XXXGb supported, default=16Kb 
+                (applications might choose an optimal value) -->
+            <parameter key="InitialBufferSize" value="16Kb"/> 
+            
+            <!-- XXKb, XXMb, or XXXGb supported, default=Unlimited (until 
+                 fails), maximum at each time step  
+                (applications might choose an optimal value) -->
+            <!-- <parameter key="MaxBufferSize" value="2Gb"/> -->
+
+            <!-- exponential growth factor > 1, default = 1.05 
+                 1.05  is good for a few large variables, for many small
+                 variables increase the value to 1.5 to 2 
+                 (optimal value is application dependent)--> 
+            <!-- <parameter key="BufferGrowthFactor" value="1.05"/> -->
+            
+        </engine>
+
+        <transport type="File">
+            
+            <!-- POSIX, stdio (C FILE*), fstream (C++) -->
+            <parameter key="Library" value="POSIX"/>
+            
+            <!-- For read/write, Microseconds (default), Milliseconds, Seconds, 
+                 Minutes, Hours. open/close always in Microseconds -->
+            <parameter key="ProfileUnits" value="Microseconds"/>
+            
+        </transport>
+        
+    </io>
+
+
+    <!--====================================
+           Configuration for the Reader 
+        ====================================-->
+
+    <io name="reader">
+        <engine type="BPFileReader">
+            
+            <!-- for vectorized memory operations, make sure your system 
+                 enables threads--> 
+            <parameter key="Threads" value="2"/>
+
+            <!-- Microseconds (default), Milliseconds, Seconds, 
+                 Minutes, Hours -->
+            <parameter key="ProfileUnits" value="Microseconds"/>
+
+        </engine>
+
+        <transport type="File">
+            
+            <!-- POSIX, stdio (C FILE*), fstream (C++) -->
+            <parameter key="Library" value="POSIX"/>
+            
+            <!-- For read/write, Microseconds (default), Milliseconds, Seconds, 
+                 Minutes, Hours. open/close always in Microseconds -->
+            <parameter key="ProfileUnits" value="Microseconds"/>
+            
+        </transport>
+        
+    </io>
+</adios-config>
diff --git a/examples/heatTransfer/read/CMakeLists.txt b/examples/heatTransfer/read/CMakeLists.txt
index 2a4ff60f7820bffb18a092572058dc7e9f0b75de..e3e143b83d77388ed31afdac45978f60c6351c26 100644
--- a/examples/heatTransfer/read/CMakeLists.txt
+++ b/examples/heatTransfer/read/CMakeLists.txt
@@ -4,16 +4,8 @@
 #------------------------------------------------------------------------------#
 
 if(ADIOS2_HAVE_MPI)
-  add_executable(heatTransfer_read_adios2 heatRead_adios2.cpp PrintData.h)
-  target_link_libraries(heatTransfer_read_adios2 adios2 MPI::MPI_C)
-
- if(ADIOS2_HAVE_HDF5)
-    add_executable(heatTransfer_read_a2h5 heatRead_a2h5.cpp PrintData.h)
-    target_link_libraries(heatTransfer_read_a2h5 adios2 MPI::MPI_C)
-  endif()
-
-  if(ADIOS2_HAVE_ADIOS1)
-    add_executable(heatTransfer_read_adios1 heatRead_adios1.cpp PrintData.h)
-    target_link_libraries(heatTransfer_read_adios1 adios1::adios MPI::MPI_C)
-  endif()
+  add_executable(heatTransfer_read heatRead.cpp PrintDataStep.h)
+  target_link_libraries(heatTransfer_read adios2 MPI::MPI_C)
+  target_compile_definitions(heatTransfer_read PRIVATE
+   -DDEFAULT_CONFIG=${CMAKE_CURRENT_SOURCE_DIR}/../heat.xml)
 endif()
diff --git a/examples/heatTransfer/read/PrintDataStep.h b/examples/heatTransfer/read/PrintDataStep.h
new file mode 100644
index 0000000000000000000000000000000000000000..17a6a737d5b32eee7293331732d89fdd136179f6
--- /dev/null
+++ b/examples/heatTransfer/read/PrintDataStep.h
@@ -0,0 +1,63 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ *
+ * PrintData.h
+ *
+ *  Created on: Apr 2017
+ *      Author: Norbert Podhorszki
+ */
+
+#ifndef PRINTDATASTEP_H_
+#define PRINTDATASTEP_H_
+
+#include <cstdint>
+#include <fstream>
+#include <iomanip>
+#include <iostream>
+#include <string>
+
+template <class T>
+void printDataStep(double *xy, T *size, T *offset, int rank, int step)
+{
+    std::ofstream myfile;
+    std::string filename = "data." + std::to_string(rank);
+    if (step == 0)
+    {
+        myfile.open(filename);
+    }
+    else
+    {
+        myfile.open(filename, std::ios::app);
+    }
+    double *data = xy;
+    uint64_t nelems = size[0] * size[1];
+    myfile << "rank=" << rank << " size=" << size[0] << "x" << size[1]
+           << " offsets=" << offset[0] << ":" << offset[1] << " step=" << step
+           << std::endl;
+
+    myfile << " time   row   columns " << offset[1] << "..."
+           << offset[1] + size[1] - 1 << std::endl;
+    myfile << "        ";
+    for (int j = 0; j < size[1]; j++)
+    {
+        myfile << std::setw(9) << offset[1] + j;
+    }
+    myfile << std::endl;
+    myfile << "------------------------------------------------------------"
+              "--\n";
+    for (int i = 0; i < size[0]; i++)
+    {
+        myfile << std::setw(5) << step << std::setw(5) << offset[0] + i;
+        for (int j = 0; j < size[1]; j++)
+        {
+            myfile << std::setw(9) << std::setprecision(2)
+                   << data[i * size[1] + j];
+        }
+        myfile << std::endl;
+    }
+    data += nelems;
+    myfile.close();
+}
+
+#endif /* PRINTDATASTEP_H_ */
diff --git a/examples/heatTransfer/read/heatRead.cpp b/examples/heatTransfer/read/heatRead.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..83bf75b660bd797dd73c2eb07dd54c44fd112d20
--- /dev/null
+++ b/examples/heatTransfer/read/heatRead.cpp
@@ -0,0 +1,159 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ *
+ * IO_ADIOS2.cpp
+ *
+ *  Created on: Nov 2017
+ *      Author: Norbert Podhorszki
+ *
+ */
+#include <mpi.h>
+
+#include "adios2.h"
+
+#include <cstdint>
+#include <iomanip>
+#include <iostream>
+#include <math.h>
+#include <memory>
+#include <stdexcept>
+#include <string>
+#include <vector>
+
+#include "PrintDataStep.h"
+
+#define str_helper(X) #X
+#define str(X) str_helper(X)
+#ifndef DEFAULT_CONFIG
+#define DEFAULT_CONFIG "../heat.xml"
+#endif
+#define DEFAULT_CONFIG_STR str(DEFAULT_CONFIG)
+
+int main(int argc, char *argv[])
+{
+    MPI_Init(&argc, &argv);
+
+    if (argc < 2)
+    {
+        std::cout << "Not enough arguments: need an input file\n";
+        return 1;
+    }
+    const char *inputfile = argv[1];
+
+    /* World comm spans all applications started with the same aprun command
+     on a Cray XK6. So we have to split and create the local
+     'world' communicator for the reader only.
+     In normal start-up, the communicator will just equal the MPI_COMM_WORLD.
+     */
+
+    int wrank, wnproc;
+    MPI_Comm_rank(MPI_COMM_WORLD, &wrank);
+    MPI_Comm_size(MPI_COMM_WORLD, &wnproc);
+    MPI_Barrier(MPI_COMM_WORLD);
+
+    const unsigned int color = 2;
+    MPI_Comm mpiReaderComm;
+    MPI_Comm_split(MPI_COMM_WORLD, color, wrank, &mpiReaderComm);
+
+    int rank, nproc;
+    MPI_Comm_rank(mpiReaderComm, &rank);
+    MPI_Comm_size(mpiReaderComm, &nproc);
+
+    adios2::ADIOS ad(std::string(DEFAULT_CONFIG_STR), mpiReaderComm,
+                     adios2::DebugON);
+
+    // Define method for engine creation
+    // 1. Get method def from config file or define new one
+
+    adios2::IO &bpReaderIO = ad.DeclareIO("reader");
+    if (!bpReaderIO.InConfigFile())
+    {
+        // if not defined by user, we can change the default settings
+        // BPFileWriter is the default engine
+        bpReaderIO.SetEngine("ADIOS1Reader");
+        bpReaderIO.SetParameters({{"num_threads", "2"}});
+
+        // ISO-POSIX file output is the default transport (called "File")
+        // Passing parameters to the transport
+        bpReaderIO.AddTransport("File", {{"verbose", "4"}});
+    }
+
+    adios2::Engine &bpReader =
+        bpReaderIO.Open(inputfile, adios2::Mode::Read, mpiReaderComm);
+
+    unsigned int gndx;
+    unsigned int gndy;
+    double *T;
+    adios2::Dims readsize;
+    adios2::Dims offset;
+    adios2::Variable<double> *vT = nullptr;
+    bool firstStep = true;
+    int step = 0;
+
+    while (true)
+    {
+        adios2::StepStatus status =
+            bpReader.BeginStep(adios2::StepMode::NextAvailable);
+        if (status != adios2::StepStatus::OK)
+            break;
+
+        if (firstStep)
+        {
+            adios2::Variable<unsigned int> *vgndx =
+                bpReaderIO.InquireVariable<unsigned int>("gndx");
+            gndx = vgndx->m_Value;
+            // bpReader.GetSync<unsigned int>("gndx", gndx);
+
+            adios2::Variable<unsigned int> *vgndy =
+                bpReaderIO.InquireVariable<unsigned int>("gndy");
+            gndy = vgndy->m_Value;
+            // bpReader.GetSync<unsigned int>("gndy", gndy);
+
+            if (rank == 0)
+            {
+                std::cout << "gndx       = " << gndx << std::endl;
+                std::cout << "gndy       = " << gndy << std::endl;
+            }
+
+            // 1D decomposition of the columns, which is inefficient for
+            // reading!
+            readsize.push_back(gndx);
+            readsize.push_back(gndy / nproc);
+            offset.push_back(0LL);
+            offset.push_back(rank * readsize[1]);
+            if (rank == nproc - 1)
+            {
+                // last process should read all the rest of columns
+                readsize[1] = gndy - readsize[1] * (nproc - 1);
+            }
+
+            std::cout << "rank " << rank << " reads " << readsize[1]
+                      << " columns from offset " << offset[1] << std::endl;
+
+            vT = bpReaderIO.InquireVariable<double>("T");
+            T = new double[readsize[0] * readsize[1]];
+
+            // Create a 2D selection for the subset
+            vT->SetSelection(adios2::Box<adios2::Dims>(offset, readsize));
+            firstStep = false;
+        }
+
+        if (!rank)
+        {
+            std::cout << "Processing step " << step << std::endl;
+        }
+        // Arrays are read by scheduling one or more of them
+        // and performing the reads at once
+        bpReader.GetDeferred<double>(*vT, T);
+        bpReader.PerformGets();
+
+        printDataStep(T, readsize.data(), offset.data(), rank, step);
+        bpReader.EndStep();
+        step++;
+    }
+    bpReader.Close();
+    delete[] T;
+    MPI_Finalize();
+    return 0;
+}
diff --git a/examples/heatTransfer/read_fileonly/CMakeLists.txt b/examples/heatTransfer/read_fileonly/CMakeLists.txt
new file mode 100644
index 0000000000000000000000000000000000000000..46c5a1e352bbf68a7c907553cfa0b50be00c98ab
--- /dev/null
+++ b/examples/heatTransfer/read_fileonly/CMakeLists.txt
@@ -0,0 +1,19 @@
+#------------------------------------------------------------------------------#
+# Distributed under the OSI-approved Apache License, Version 2.0.  See
+# accompanying file Copyright.txt for details.
+#------------------------------------------------------------------------------#
+
+if(ADIOS2_HAVE_MPI)
+  add_executable(heatTransfer_read_fileonly_adios2 heatRead_adios2.cpp PrintData.h)
+  target_link_libraries(heatTransfer_read_fileonly_adios2 adios2 MPI::MPI_C)
+
+ if(ADIOS2_HAVE_HDF5)
+    add_executable(heatTransfer_read_fileonly_a2h5 heatRead_a2h5.cpp PrintData.h)
+    target_link_libraries(heatTransfer_read_fileonly_a2h5 adios2 MPI::MPI_C)
+  endif()
+
+  if(ADIOS2_HAVE_ADIOS1)
+    add_executable(heatTransfer_read_fileonly_adios1 heatRead_adios1.cpp PrintData.h)
+    target_link_libraries(heatTransfer_read_fileonly_adios1 adios1::adios MPI::MPI_C)
+  endif()
+endif()
diff --git a/examples/heatTransfer/read/PrintData.h b/examples/heatTransfer/read_fileonly/PrintData.h
similarity index 100%
rename from examples/heatTransfer/read/PrintData.h
rename to examples/heatTransfer/read_fileonly/PrintData.h
diff --git a/examples/heatTransfer/read/heatRead_a2h5.cpp b/examples/heatTransfer/read_fileonly/heatRead_a2h5.cpp
similarity index 100%
rename from examples/heatTransfer/read/heatRead_a2h5.cpp
rename to examples/heatTransfer/read_fileonly/heatRead_a2h5.cpp
diff --git a/examples/heatTransfer/read/heatRead_adios1.cpp b/examples/heatTransfer/read_fileonly/heatRead_adios1.cpp
similarity index 100%
rename from examples/heatTransfer/read/heatRead_adios1.cpp
rename to examples/heatTransfer/read_fileonly/heatRead_adios1.cpp
diff --git a/examples/heatTransfer/read/heatRead_adios2.cpp b/examples/heatTransfer/read_fileonly/heatRead_adios2.cpp
similarity index 97%
rename from examples/heatTransfer/read/heatRead_adios2.cpp
rename to examples/heatTransfer/read_fileonly/heatRead_adios2.cpp
index f4a595572101c8176298c48773b1ba2f686e7b6b..a0833fa1075a15ba70b7461123c73d8b13e61db7 100644
--- a/examples/heatTransfer/read/heatRead_adios2.cpp
+++ b/examples/heatTransfer/read_fileonly/heatRead_adios2.cpp
@@ -44,7 +44,7 @@ int main(int argc, char *argv[])
     MPI_Comm_rank(mpiReaderComm, &rank);
     MPI_Comm_size(mpiReaderComm, &nproc);
 
-    adios2::ADIOS ad("adios2.xml", mpiReaderComm, adios2::DebugON);
+    adios2::ADIOS ad(mpiReaderComm, adios2::DebugON);
 
     // Define method for engine creation
     // 1. Get method def from config file or define new one
@@ -56,6 +56,7 @@ int main(int argc, char *argv[])
         // BPFileWriter is the default engine
         bpReaderIO.SetEngine("ADIOS1Reader");
         bpReaderIO.SetParameters({{"num_threads", "2"}});
+        bpReaderIO.SetParameter("OpenAsFile", "true");
 
         // ISO-POSIX file is the default transport
         // Passing parameters to the transport
diff --git a/source/adios2/helper/adiosXML.cpp b/source/adios2/helper/adiosXML.cpp
index 2a7764cea9f3c5ed0619eca78a45308ca0038303..7045fc2b9cfffcd21f091b916816e7f44e2b5f55 100644
--- a/source/adios2/helper/adiosXML.cpp
+++ b/source/adios2/helper/adiosXML.cpp
@@ -164,6 +164,13 @@ void InitXML(const std::string configXML, MPI_Comm mpiComm,
 
     fileContents = BroadcastValue(fileContents, mpiComm);
 
+    if (debugMode && fileContents.empty())
+    {
+        throw std::invalid_argument("ERROR: config xml file " + configXML +
+                                    " is either empty or file couldn't be "
+                                    "found, in call to ADIOS constructor\n");
+    }
+
     pugi::xml_document doc;
     auto parse_result = doc.load_buffer_inplace(
         const_cast<char *>(fileContents.data()), fileContents.size());
diff --git a/source/adios2/toolkit/format/bp3/BP3Deserializer.tcc b/source/adios2/toolkit/format/bp3/BP3Deserializer.tcc
index 3d49306b639e086e0ed07fe2d033680913d835e3..7fb69ef26c6af86023931eaaf4bb1929245e1d8e 100644
--- a/source/adios2/toolkit/format/bp3/BP3Deserializer.tcc
+++ b/source/adios2/toolkit/format/bp3/BP3Deserializer.tcc
@@ -123,6 +123,7 @@ BP3Deserializer::DefineVariableInIO(const ElementIndexHeader &header, IO &io,
     {
         std::lock_guard<std::mutex> lock(m_Mutex);
         variable = &io.DefineVariable<T>(variableName);
+        variable->m_Value = characteristics.Statistics.Value;
         variable->m_Min = characteristics.Statistics.Value;
         variable->m_Max = characteristics.Statistics.Value;
     }