diff --git a/cmake/FindADIOS1.cmake b/cmake/FindADIOS1.cmake
new file mode 100644
index 0000000000000000000000000000000000000000..da0fdd08dbf1ae6c6f0f3257c719a9a8734d01d1
--- /dev/null
+++ b/cmake/FindADIOS1.cmake
@@ -0,0 +1,260 @@
+# - Find ADIOS 1.x library, routines for scientific, parallel IO
+#   https://www.olcf.ornl.gov/center-projects/adios/
+#
+# Use this module by invoking find_package with the form:
+#   find_package(ADIOS1
+#     [version] [EXACT]     # Minimum or EXACT version, e.g. 1.6.0
+#     [REQUIRED]            # Fail with an error if ADIOS or a required
+#                           #   component is not found
+#     [QUIET]               # ...
+#     [COMPONENTS <...>]    # Compiled in components: fortran, readonly, 
+                            # sequential (all are case insentative) 
+#   )
+#
+# Module that finds the includes and libraries for a working ADIOS 1.x install.
+# This module invokes the `adios_config` script that should be installed with
+# the other ADIOS tools.
+#
+# To provide a hint to the module where to find the ADIOS installation,
+# set the ADIOS1_ROOT or ADIOS1_DIR environment variable.
+#
+# If this variable is not set, make sure that at least the according `bin/`
+# directory of ADIOS 1.x is in your PATH environment variable.
+#
+# Set the following CMake variables BEFORE calling find_packages to
+# influence this module:
+#   ADIOS1_USE_STATIC_LIBS - Set to ON to force the use of static
+#                           libraries.  Default: OFF
+#
+# This module will define the following variables:
+#   ADIOS1_INCLUDE_DIRS    - Include directories for the ADIOS 1.x headers.
+#   ADIOS1_LIBRARY_PATH    - Full path of the libadios library (.a or .so file)
+#   ADIOS1_DEPENDENCY_LIBRARIES       - ADIOS 1.x dependency libraries.
+#   ADIOS1_FOUND           - TRUE if FindADIOS1 found a working install
+#   ADIOS1_VERSION         - Version in format Major.Minor.Patch
+#
+# Not used for now:
+#   ADIOS1_DEFINITIONS     - Compiler definitions you should add with
+#                           add_definitions(${ADIOS1_DEFINITIONS})
+#
+# Example to find ADIOS 1.x (default)
+# find_package(ADIOS1)
+# if(ADIOS1_FOUND)
+#   include_directories(${ADIOS1_INCLUDE_DIRS})
+#   add_executable(foo foo.c)
+#   target_link_libraries(foo ${ADIOS1_LIBRARY_PATH} ADIOS1_DEPENDENCY_LIBRARIES)
+# endif()
+
+# Example to find ADIOS 1.x using component
+# find_package(ADIOS1 COMPONENTS fortran)
+# if(ADIOS1_FOUND)
+#   include_directories(${ADIOS1_INCLUDE_DIRS})
+#   add_executable(foo foo.c)
+#   target_link_libraries(foo ${ADIOS1_LIBRARY_PATH} ${ADIOS1_DEPENDENCY_LIBRARIES})
+# endif()
+###############################################################################
+#Copyright (c) 2014, Axel Huebl and Felix Schmitt from http://picongpu.hzdr.de
+#All rights reserved.
+
+#Redistribution and use in source and binary forms, with or without
+#modification, are permitted provided that the following conditions are met:
+
+#1. Redistributions of source code must retain the above copyright notice, this
+#list of conditions and the following disclaimer.
+
+#2. Redistributions in binary form must reproduce the above copyright notice,
+#this list of conditions and the following disclaimer in the documentation
+#and/or other materials provided with the distribution.
+
+#3. Neither the name of the copyright holder nor the names of its contributors
+#may be used to endorse or promote products derived from this software without
+#specific prior written permission.
+
+#THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+#AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+#IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+#DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
+#FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+#DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
+#SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
+#CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+#OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+#OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+###############################################################################
+
+
+###############################################################################
+# Required cmake version
+###############################################################################
+
+cmake_minimum_required(VERSION 2.8.5)
+
+
+###############################################################################
+# ADIOS
+###############################################################################
+# get flags for adios_config, -l is the default
+#-f for fortran, -r for readonly, -s for sequential (nompi)
+set(OPTLIST "-l")
+if(ADIOS1_FIND_COMPONENTS)
+    foreach(COMP ${ADIOS1_FIND_COMPONENTS})
+        string(TOLOWER ${COMP} comp)
+        if(comp STREQUAL "fortran")
+            set(OPTLIST "${OPTLIST}f")
+        elseif(comp STREQUAL "readonly")
+            set(OPTLIST "${OPTLIST}r")
+        elseif(comp STREQUAL "sequential")
+            set(OPTLIST "${OPTLIST}s")
+        else()
+            message("ADIOS 1.x component ${COMP} is not supported. Please use fortran, readonly, or sequential")
+        endif()
+    endforeach()
+endif()
+
+# we start by assuming we found ADIOS and falsify it if some
+# dependencies are missing (or if we did not find ADIOS at all)
+set(ADIOS1_FOUND TRUE)
+
+
+# find `adios_config` program #################################################
+#   check the ADIOS1_ROOT and ADIOS1_DIR hint and the normal PATH
+find_file(ADIOS1_CONFIG
+    NAME adios_config
+    PATHS $ENV{ADIOS1_ROOT}/bin $ENV{ADIOS1_DIR}/bin $ENV{INSTALL_PREFIX}/bin $ENV{PATH})
+
+if(ADIOS1_CONFIG)
+    message(STATUS "Found 'adios_config': ${ADIOS1_CONFIG}")
+else(ADIOS1_CONFIG)
+    set(ADIOS1_FOUND FALSE)
+    message(STATUS "Can NOT find 'adios_config' - set ADIOS1_ROOT, ADIOS1_DIR or INSTALL_PREFIX, or check your PATH")
+endif(ADIOS1_CONFIG)
+
+# check `adios_config` program ################################################
+if(ADIOS1_FOUND)
+    execute_process(COMMAND ${ADIOS1_CONFIG} ${OPTLIST}
+                    OUTPUT_VARIABLE ADIOS1_LINKFLAGS
+                    RESULT_VARIABLE ADIOS1_CONFIG_RETURN
+                    OUTPUT_STRIP_TRAILING_WHITESPACE)
+    if(NOT ADIOS1_CONFIG_RETURN EQUAL 0)
+        set(ADIOS1_FOUND FALSE)
+        message(STATUS "Can NOT execute 'adios_config' - check file permissions")
+    endif()
+
+    # find ADIOS1_ROOT_DIR
+    execute_process(COMMAND ${ADIOS1_CONFIG} -d
+                    OUTPUT_VARIABLE ADIOS1_ROOT_DIR
+                    OUTPUT_STRIP_TRAILING_WHITESPACE)
+    if(NOT IS_DIRECTORY "${ADIOS1_ROOT_DIR}")
+        set(ADIOS1_FOUND FALSE)
+        message(STATUS "The directory provided by 'adios_config -d' does not exist: ${ADIOS1_ROOT_DIR}")
+    endif()
+endif(ADIOS1_FOUND)
+
+# option: use only static libs ################################################
+if(ADIOS1_USE_STATIC_LIBS)
+    # carfully: we have to restore the original path in the end
+    set(_ORIG_CMAKE_FIND_LIBRARY_SUFFIXES ${CMAKE_FIND_LIBRARY_SUFFIXES})
+    set(CMAKE_FIND_LIBRARY_SUFFIXES .a)
+endif()
+
+
+# we found something in ADIOS1_ROOT_DIR and adios_config works #################
+if(ADIOS1_FOUND)
+    # ADIOS headers
+    list(APPEND ADIOS1_INCLUDE_DIRS ${ADIOS1_ROOT_DIR}/include)
+
+    # check for compiled in dependencies, recomve ";" in ADIOS1_LINKFLAGS (from cmake build)
+    string(REGEX REPLACE ";" " " ADIOS1_LINKFLAGS "${ADIOS1_LINKFLAGS}")
+    message(STATUS "  ADIOS1 linker flags (unparsed): ${ADIOS1_LINKFLAGS}")
+
+    # find all library paths -L
+    #   note: this can cause trouble if some libs are specified twice from
+    #         different sources (quite unlikely)
+    #         http://www.cmake.org/pipermail/cmake/2008-November/025128.html
+    set(ADIOS1_LIBRARY_DIRS "")
+    string(REGEX MATCHALL " -L([A-Za-z_0-9/\\.-]+)" _ADIOS1_LIBDIRS " ${ADIOS1_LINKFLAGS}")
+    foreach(_LIBDIR ${_ADIOS1_LIBDIRS})
+        string(REPLACE " -L" "" _LIBDIR ${_LIBDIR})
+        list(APPEND ADIOS1_LIBRARY_DIRS ${_LIBDIR})
+    endforeach()
+    # we could append ${CMAKE_PREFIX_PATH} now but that is not really necessary
+
+    #message(STATUS "ADIOS1 DIRS to look for libs: ${ADIOS1_LIBRARY_DIRS}")
+
+    # parse all -lname libraries and find an absolute path for them
+    string(REGEX MATCHALL " -l([A-Za-z_0-9\\.-]+)" _ADIOS1_LIBS " ${ADIOS1_LINKFLAGS}")
+    foreach(_LIB ${_ADIOS1_LIBS})
+        string(REPLACE " -l" "" _LIB ${_LIB})
+
+        # find static lib: absolute path in -L then default
+        find_library(_LIB_DIR NAMES ${_LIB} PATHS ${ADIOS1_LIBRARY_DIRS} CMAKE_FIND_ROOT_PATH_BOTH)
+
+        # found?
+        if(_LIB_DIR)
+            if(_LIB STREQUAL "adios")
+                message(STATUS "  Found the main adios library in ${_LIB_DIR}")
+                set(ADIOS1_LIBRARY_PATH "${_LIB_DIR}")
+                #message(STATUS "    ADIOS1_LIBRARY_PATH set to ${ADIOS1_LIBRARY_PATH}")
+            else()
+                message(STATUS "  Found ${_LIB} in ${_LIB_DIR}")
+                list(APPEND ADIOS1_DEPENDENCY_LIBRARIES "${_LIB_DIR}")
+            endif()
+        else(_LIB_DIR)
+            set(ADIOS1_FOUND FALSE)
+            message(STATUS "ADIOS1: Could NOT find library '${_LIB}'")
+        endif(_LIB_DIR)
+
+        # clean cached var
+        unset(_LIB_DIR CACHE)
+        unset(_LIB_DIR)
+    endforeach()
+
+    #add libraries which are already using cmake format
+    string(REGEX MATCHALL "/([A-Za-z_0-9/\\.-]+)\\.([a|so]+)" _ADIOS1_LIBS_SUB "${ADIOS1_LINKFLAGS}")
+    list(APPEND ADIOS1_DEPENDENCY_LIBRARIES "${_ADIOS1_LIBS_SUB}")
+
+    # add the version string
+    execute_process(COMMAND ${ADIOS1_CONFIG} -v
+                    OUTPUT_VARIABLE ADIOS1_VERSION
+                    OUTPUT_STRIP_TRAILING_WHITESPACE)
+    
+endif(ADIOS1_FOUND)
+
+# unset checked variables if not found
+if(NOT ADIOS1_FOUND)
+    unset(ADIOS1_INCLUDE_DIRS)
+    unset(ADIOS1_DEPENDENCY_LIBRARIES)
+    unset(ADIOS1_LIBRARY_PATH)
+endif(NOT ADIOS1_FOUND)
+
+
+# restore CMAKE_FIND_LIBRARY_SUFFIXES if manipulated by this module ###########
+if(ADIOS1_USE_STATIC_LIBS)
+    set(CMAKE_FIND_LIBRARY_SUFFIXES ${_ORIG_CMAKE_FIND_LIBRARY_SUFFIXES})
+endif()
+
+
+###############################################################################
+# FindPackage Options
+###############################################################################
+
+# handles the REQUIRED, QUIET and version-related arguments for find_package
+include(FindPackageHandleStandardArgs)
+find_package_handle_standard_args(ADIOS1
+    REQUIRED_VARS ADIOS1_LIBRARY_PATH ADIOS1_DEPENDENCY_LIBRARIES ADIOS1_INCLUDE_DIRS
+    VERSION_VAR ADIOS1_VERSION
+)
+
+##########################################################################
+# Add target and dependencies to ADIOS2
+##########################################################################
+#message(STATUS "ADIOS1 Find ended with ${ADIOS1_FOUND}")
+    if(ADIOS1_FOUND AND NOT TARGET adios1::adios)
+      message(STATUS "Add library ADIOS1 to the build")
+      add_library(adios1::adios UNKNOWN IMPORTED)
+      set_target_properties(adios1::adios PROPERTIES
+        IMPORTED_LOCATION "${ADIOS1_LIBRARY_PATH}"
+        INTERFACE_LINK_LIBRARIES "${ADIOS1_DEPENDENCY_LIBRARIES}"
+        INTERFACE_INCLUDE_DIRECTORIES "${ADIOS1_INCLUDE_DIRS}"
+      )
+    endif()
diff --git a/examples/CMakeLists.txt b/examples/CMakeLists.txt
index ffe6d00e4d8057f0e861d7e2209d16b7f2b26fe6..59d0aaef3e1741211ad8274c17dc9f2b361b879b 100644
--- a/examples/CMakeLists.txt
+++ b/examples/CMakeLists.txt
@@ -4,3 +4,4 @@
 #------------------------------------------------------------------------------#
 
 add_subdirectory(hello)
+add_subdirectory(heatTransfer)
diff --git a/examples/heatTransfer/CMakeLists.txt b/examples/heatTransfer/CMakeLists.txt
new file mode 100644
index 0000000000000000000000000000000000000000..bca588c58d2509e99148fb0d384df8b7a6b916f6
--- /dev/null
+++ b/examples/heatTransfer/CMakeLists.txt
@@ -0,0 +1,29 @@
+#------------------------------------------------------------------------------#
+# Distributed under the OSI-approved Apache License, Version 2.0.  See
+# accompanying file Copyright.txt for details.
+#------------------------------------------------------------------------------#
+
+add_executable(heatTransfer_adios main.cpp HeatTransfer.cpp Settings.cpp IO_adios2.cpp)
+
+if(ADIOS_USE_MPI)
+    find_package(MPI COMPONENTS C REQUIRED)
+    target_include_directories(heatTransfer_adios PRIVATE ${MPI_C_INCLUDE_PATH})
+    target_link_libraries(heatTransfer_adios adios2 ${MPI_C_LIBRARIES})
+else(ADIOS_USE_MPI) 
+    target_link_libraries(heatTransfer_adios adios2)
+endif()
+
+if(ADIOS_USE_ADIOS1)
+    find_package(ADIOS1 REQUIRED)
+    add_executable(heatTransfer_adios1 main.cpp HeatTransfer.cpp Settings.cpp IO_adios1.cpp)
+    if(ADIOS_USE_MPI)
+        target_include_directories(heatTransfer_adios1 PRIVATE ${MPI_C_INCLUDE_PATH})
+        target_link_libraries(heatTransfer_adios1  adios1::adios ${MPI_C_LIBRARIES})
+    else(ADIOS_USE_MPI) 
+        target_compile_definitions(heatTransfer_adios1 PRIVATE -D_NOMPI)
+        target_link_libraries(heatTransfer_adios1 adios1::adios)
+    endif()
+endif()
+
+add_subdirectory(read)
+
diff --git a/examples/heatTransfer/HeatTransfer.cpp b/examples/heatTransfer/HeatTransfer.cpp
index ac706e4c66d75c5e342faa915ae2edb8aa4519e2..29283fa776a39650cec330d1688402a6b7f83299 100644
--- a/examples/heatTransfer/HeatTransfer.cpp
+++ b/examples/heatTransfer/HeatTransfer.cpp
@@ -10,7 +10,6 @@
  *     Author: Norbert Podhorszki
  *
  */
-#include <mpi.h>
 
 #include <iomanip>
 #include <iostream>
diff --git a/examples/heatTransfer/HeatTransfer.h b/examples/heatTransfer/HeatTransfer.h
index 7d48eb558d2db274218e8b0030ad53cc2aa0f7f3..5233d3f5f48fdbc200149b4423c9c3824a4006dc 100644
--- a/examples/heatTransfer/HeatTransfer.h
+++ b/examples/heatTransfer/HeatTransfer.h
@@ -11,7 +11,10 @@
 #ifndef HEATTRANSFER_H_
 #define HEATTRANSFER_H_
 
+#define OMPI_SKIP_MPICXX 1 // workaround for OpenMPI forcing C++ bindings
 #include <mpi.h>
+#undef OMPI_SKIP_MPICXX
+
 #include <vector>
 
 #include "Settings.h"
diff --git a/examples/heatTransfer/IO.h b/examples/heatTransfer/IO.h
index 999866112e471e46f2136f804ed2ee5226bb0a0a..0f774336f18e81cee951f4c5879f7733e2f21943 100644
--- a/examples/heatTransfer/IO.h
+++ b/examples/heatTransfer/IO.h
@@ -13,7 +13,10 @@
 
 #include "HeatTransfer.h"
 #include "Settings.h"
+
+#define OMPI_SKIP_MPICXX 1 // workaround for OpenMPI forcing C++ bindings
 #include <mpi.h>
+#undef OMPI_SKIP_MPICXX
 
 class IO
 {
diff --git a/examples/heatTransfer/IO_adios2.cpp b/examples/heatTransfer/IO_adios2.cpp
index ac0567820549d3300ca410c9686fe8552fb9578f..966bfae203b9d3cc67332d12b923d624546ccdac 100644
--- a/examples/heatTransfer/IO_adios2.cpp
+++ b/examples/heatTransfer/IO_adios2.cpp
@@ -31,7 +31,7 @@ IO::IO(const Settings &s, MPI_Comm comm)
     if (!bpWriterSettings.isUserDefined())
     {
         // if not defined by user, we can change the default settings
-        bpWriterSettings.SetEngine("BP"); // BP is the default engine
+        bpWriterSettings.SetEngine("BPFileWriter"); // BP is the default engine
         bpWriterSettings.AllowThreads(
             1); // allow 1 extra thread for data processing
         bpWriterSettings.AddTransport(
@@ -47,11 +47,13 @@ IO::IO(const Settings &s, MPI_Comm comm)
 
     // define T as 2D global array
     varT = &ad->DefineVariable<double>(
-        "T", {s.gndx, s.gndy}, // Global dimensions
-        {s.ndx,
-         s.ndy}, // local size, could be defined later using SetSelection()
-        {s.offsx, s.offsy} // offset of the local array in the global space
-        );
+        "T",
+        // Global dimensions
+        {s.gndx, s.gndy},
+        // local size, could be defined later using SetSelection()
+        {s.ndx, s.ndy},
+        // offset of the local array in the global space
+        {s.offsx, s.offsy});
 
     // add transform to variable
     // adios::Transform tr = adios::transform::BZIP2( );
@@ -71,28 +73,19 @@ IO::~IO()
     delete ad;
 }
 
-void /*IO::*/ old_style_write(int step, const HeatTransfer &ht,
-                              const Settings &s, MPI_Comm comm)
-{
-    bpWriter->Write<double>(*varT, ht.data_noghost().data());
-    bpWriter->Advance();
-}
-
 void IO::write(int step, const HeatTransfer &ht, const Settings &s,
                MPI_Comm comm)
 {
+#if 1
+
     /* This selection is redundant and not required, since we defined
      * the selection already in DefineVariable(). It is here just as an example.
      */
     // Make a selection to describe the local dimensions of the variable we
-    // write
-    // and
-    // its offsets in the global spaces. This could have been done in
+    // write and its offsets in the global spaces. This could have been done in
     // adios.DefineVariable()
-    adios::Selection sel = adios.SelectionBoundingBox(
-        {s.ndx, s.ndy},
-        {s.offsx, s.offsy}); // local dims and offsets; both as list
-    var2D.SetSelection(sel);
+    adios::SelectionBoundingBox sel({s.ndx, s.ndy}, {s.offsx, s.offsy});
+    varT->SetSelection(sel);
 
     /* Select the area that we want to write from the data pointer we pass to
        the
@@ -105,10 +98,17 @@ void IO::write(int step, const HeatTransfer &ht, const Settings &s,
        above.
        Default memspace is always the full selection.
     */
-    adios::Selection memspace =
-        adios.SelectionBoundingBox({s.ndx, s.ndy}, {1, 1});
-    var2D.SetMemorySelection(memspace);
+    adios::SelectionBoundingBox memspace =
+        adios::SelectionBoundingBox({s.ndx, s.ndy}, {1, 1});
+    varT->SetMemorySelection(memspace);
 
-    bpWriter->Write<double>(*varT, ht.data());
+    bpWriter->Write<double>(*varT, ht.data_noghost().data());
     bpWriter->Advance();
+
+#else
+
+    bpWriter->Write<double>(*varT, ht.data_noghost().data());
+    bpWriter->Advance();
+
+#endif
 }
diff --git a/examples/heatTransfer/main.cpp b/examples/heatTransfer/main.cpp
index 1d1372f401ff641f3dc0da71a1b175b9b5c5b1fb..ff1b6c44c9a5e0cbf836f60b475c3190d7e34e8f 100644
--- a/examples/heatTransfer/main.cpp
+++ b/examples/heatTransfer/main.cpp
@@ -10,7 +10,9 @@
  *     Author: Norbert Podhorszki
  *
  */
+#define OMPI_SKIP_MPICXX 1 // workaround for OpenMPI forcing C++ bindings
 #include <mpi.h>
+#undef OMPI_SKIP_MPICXX
 
 #include <iostream>
 #include <memory>
@@ -64,10 +66,10 @@ int main(int argc, char *argv[])
         IO io(settings, mpiHeatTransferComm);
 
         ht.init(true);
-        ht.printT("Initialized T:", mpiHeatTransferComm);
+        // ht.printT("Initialized T:", mpiHeatTransferComm);
         ht.heatEdges();
-        // ht.exchange( mpiHeatTransferComm );
-        ht.printT("Heated T:", mpiHeatTransferComm);
+        ht.exchange(mpiHeatTransferComm);
+        // ht.printT("Heated T:", mpiHeatTransferComm);
         io.write(0, ht, settings, mpiHeatTransferComm);
 
         for (unsigned int t = 1; t <= settings.steps; ++t)
diff --git a/examples/heatTransfer/read/CMakeLists.txt b/examples/heatTransfer/read/CMakeLists.txt
new file mode 100644
index 0000000000000000000000000000000000000000..993d1d0474d30711d04b45206f366efecee04fcc
--- /dev/null
+++ b/examples/heatTransfer/read/CMakeLists.txt
@@ -0,0 +1,27 @@
+#------------------------------------------------------------------------------#
+# Distributed under the OSI-approved Apache License, Version 2.0.  See
+# accompanying file Copyright.txt for details.
+#------------------------------------------------------------------------------#
+
+#add_executable(heatRead_adios heatRead_adios.cpp)
+#
+#if(ADIOS_USE_MPI)
+#    find_package(MPI COMPONENTS C REQUIRED)
+#    target_include_directories(heatRead_adios PRIVATE ${MPI_C_INCLUDE_PATH})
+#    target_link_libraries(heatRead_adios adios2 ${MPI_C_LIBRARIES})
+#else(ADIOS_USE_MPI) 
+#    target_link_libraries(heatRead_adios adios2)
+#endif()
+
+if(ADIOS_USE_ADIOS1)
+    find_package(ADIOS1 REQUIRED)
+    add_executable(heatRead_adios1 heatRead_adios1.cpp PrintData.cpp)
+    if(ADIOS_USE_MPI)
+        target_include_directories(heatRead_adios1 PRIVATE ${MPI_C_INCLUDE_PATH})
+        target_link_libraries(heatRead_adios1  adios1::adios ${MPI_C_LIBRARIES})
+    else(ADIOS_USE_MPI) 
+        target_compile_definitions(heatRead_adios1 PRIVATE -D_NOMPI)
+        target_link_libraries(heatRead_adios1 adios1::adios)
+    endif()
+endif()
+
diff --git a/examples/heatTransfer/read/PrintData.cpp b/examples/heatTransfer/read/PrintData.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..030fa561f1cc1a6e3dc62b24d8cf45f98583bfcd
--- /dev/null
+++ b/examples/heatTransfer/read/PrintData.cpp
@@ -0,0 +1,54 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ *
+ * PrintData.cpp
+ *
+ *  Created on: Apr 2017
+ *      Author: Norbert Podhorszki
+ */
+
+#include "PrintData.h"
+#include <fstream>
+#include <iomanip>
+#include <iostream>
+#include <string>
+
+void printData(double *xy, uint64_t *size, uint64_t *offset, int rank,
+               int steps)
+{
+    std::ofstream myfile;
+    std::string filename = "data." + std::to_string(rank);
+    myfile.open(filename);
+    double *data = xy;
+    uint64_t nelems = size[0] * size[1];
+    for (int step = 0; step < steps; step++)
+    {
+        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();
+}
diff --git a/examples/heatTransfer/read/PrintData.h b/examples/heatTransfer/read/PrintData.h
new file mode 100644
index 0000000000000000000000000000000000000000..308ace34007f88c15498464b1555b5cca3ed1f6b
--- /dev/null
+++ b/examples/heatTransfer/read/PrintData.h
@@ -0,0 +1,19 @@
+/*
+ * 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 PRINTDATA_H_
+#define PRINTDATA_H_
+
+#include <cstdint>
+
+void printData(double *xy, uint64_t *size, uint64_t *offset, int rank,
+               int steps);
+
+#endif /* PRINTDATA_H_ */
diff --git a/examples/heatTransfer/read/heatRead_adios1.cpp b/examples/heatTransfer/read/heatRead_adios1.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d596d223efd8c5b11d06d42f0881ec85f15ffe34
--- /dev/null
+++ b/examples/heatTransfer/read/heatRead_adios1.cpp
@@ -0,0 +1,104 @@
+
+#define OMPI_SKIP_MPICXX 1 // workaround for OpenMPI forcing C++ bindings
+#include <mpi.h>
+#undef OMPI_SKIP_MPICXX
+
+#include "adios_read.h"
+#include <cstdint>
+#include <iomanip>
+#include <iostream>
+#include <math.h>
+#include <memory>
+#include <stdexcept>
+#include <string>
+
+#include "PrintData.h"
+
+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);
+
+    adios_read_init_method(ADIOS_READ_METHOD_BP, mpiReaderComm, "verbose=3");
+
+    ADIOS_FILE *f;
+    f = adios_read_open_file(inputfile, ADIOS_READ_METHOD_BP, mpiReaderComm);
+    if (f == NULL)
+    {
+        std::cout << adios_errmsg() << std::endl;
+        return -1;
+    }
+
+    ADIOS_VARINFO *vgndx = adios_inq_var(f, "gndx");
+    ADIOS_VARINFO *vgndy = adios_inq_var(f, "gndy");
+
+    unsigned int gndx = *(unsigned int *)vgndx->value;
+    unsigned int gndy = *(unsigned int *)vgndy->value;
+
+    if (rank == 0)
+    {
+        std::cout << "gndx = " << gndx << std::endl;
+        std::cout << "gndy = " << gndy << std::endl;
+    }
+    adios_free_varinfo(vgndx);
+    adios_free_varinfo(vgndy);
+
+    // 1D decomposition of the columns, which is inefficient for reading!
+    uint64_t readsize[2] = {gndx, gndy / nproc};
+    uint64_t offset[2] = {0LL, 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;
+
+    ADIOS_VARINFO *vT = adios_inq_var(f, "T");
+
+    double *T = new double[vT->nsteps * readsize[0] * readsize[1]];
+
+    // Create a 2D selection for the subset
+    ADIOS_SELECTION *sel = adios_selection_boundingbox(2, offset, readsize);
+
+    // Arrays are read by scheduling one or more of them
+    // and performing the reads at once
+    adios_schedule_read(f, sel, "T", 0, vT->nsteps, T);
+    adios_perform_reads(f, 1);
+
+    printData(T, readsize, offset, rank, vT->nsteps);
+    adios_read_close(f);
+    adios_free_varinfo(vT);
+    delete[] T;
+    // Terminate
+    adios_selection_delete(sel);
+    adios_read_finalize_method(ADIOS_READ_METHOD_BP);
+    MPI_Finalize();
+    return 0;
+}
diff --git a/examples/hello/adios1Writer/CMakeLists.txt b/examples/hello/adios1Writer/CMakeLists.txt
new file mode 100644
index 0000000000000000000000000000000000000000..b38cfb90d3a153197efaa99f88295187debcfc1b
--- /dev/null
+++ b/examples/hello/adios1Writer/CMakeLists.txt
@@ -0,0 +1,14 @@
+#------------------------------------------------------------------------------#
+# Distributed under the OSI-approved Apache License, Version 2.0.  See
+# accompanying file Copyright.txt for details.
+#------------------------------------------------------------------------------#
+
+if(ADIOS_USE_MPI)
+  find_package(MPI COMPONENTS C REQUIRED)
+  add_executable(hello_adios1Writer helloADIOS1Writer.cpp)
+  target_include_directories(hello_adios1Writer PRIVATE ${MPI_C_INCLUDE_PATH})
+  target_link_libraries(hello_adios1Writer adios2 ${MPI_C_LIBRARIES})
+endif()
+
+add_executable(hello_adios1Writer_nompi helloADIOS1Writer_nompi.cpp)
+target_link_libraries(hello_adios1Writer_nompi adios2)
diff --git a/examples/hello/adios1Writer/helloADIOS1Writer.cpp b/examples/hello/adios1Writer/helloADIOS1Writer.cpp
index 2a7803ab6edac9adc2618699fb3be45c3960b6c7..87101533b4795379e3b2c94966c44d01fea83403 100644
--- a/examples/hello/adios1Writer/helloADIOS1Writer.cpp
+++ b/examples/hello/adios1Writer/helloADIOS1Writer.cpp
@@ -11,7 +11,9 @@
 #include <iostream>
 #include <vector>
 
+#define OMPI_SKIP_MPICXX 1 // workaround for OpenMPI forcing C++ bindings
 #include <mpi.h>
+#undef OMPI_SKIP_MPICXX
 
 #include "ADIOS_CPP.h"
 
diff --git a/examples/hello/adios1Writer/helloADIOS1Writer_nompi.cpp b/examples/hello/adios1Writer/helloADIOS1Writer_nompi.cpp
index 44d4d5547050e79ef4a3cb3b0222b4d21433438f..5955b33436df32cd835391a75c85bf2bc8f7f53b 100644
--- a/examples/hello/adios1Writer/helloADIOS1Writer_nompi.cpp
+++ b/examples/hello/adios1Writer/helloADIOS1Writer_nompi.cpp
@@ -16,7 +16,7 @@
 int main(int argc, char *argv[])
 {
     const bool adiosDebug = true;
-    adios::ADIOS adios(adiosDebug);
+    adios::ADIOS adios(adios::Verbose::INFO, adiosDebug);
 
     // Application variable
     std::vector<double> myDoubles = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
diff --git a/include/core/VariableBase.h b/include/core/VariableBase.h
index eea1d261c67e63b84e1db385117dfcb01781a9ce..d9d98c9160c341a9153ddd8fa7869af92590331f 100644
--- a/include/core/VariableBase.h
+++ b/include/core/VariableBase.h
@@ -12,14 +12,16 @@
 #define VARIABLEBASE_H_
 
 /// \cond EXCLUDE_FROM_DOXYGEN
+#include <exception>
 #include <iterator>
 #include <sstream>
 #include <string>
 #include <vector>
 /// \endcond
 
-#include "functions/adiosFunctions.h" //GetTotalSize
-#include "functions/adiosTemplates.h" //GetType<T>
+#include "functions/adiosFunctions.h" //GetTotalSize, ConvertUint64VectorToSizetVector
+#include "functions/adiosTemplates.h"       //GetType<T>
+#include "selection/SelectionBoundingBox.h" //Selection
 
 namespace adios
 {
@@ -71,11 +73,62 @@ public:
         return GetTotalSize(m_Dimensions);
     }
 
+    /**
+     * Set the local dimension and global offset of the variable using a
+     * selection
+     * Only bounding boxes are allowed
+     */
+    void SetSelection(const SelectionBoundingBox &sel)
+    {
+
+        if (m_GlobalDimensions.size() == 0)
+        {
+            throw std::invalid_argument("Variable.SetSelection() is an invalid "
+                                        "call for single value variables\n");
+        }
+        if (m_GlobalDimensions.size() != sel.m_Count.size())
+        {
+            throw std::invalid_argument("Variable.SetSelection() bounding box "
+                                        "dimension must equal the global "
+                                        "dimension of the variable\n");
+        }
+
+        ConvertUint64VectorToSizetVector(sel.m_Count, m_Dimensions);
+        ConvertUint64VectorToSizetVector(sel.m_Start, m_GlobalDimensions);
+    }
+
+    /**
+     * Set the local dimension and global offset of the variable using a
+     * selection
+     * Only bounding boxes are allowed
+     */
+    void SetMemorySelection(const SelectionBoundingBox &sel)
+    {
+        if (m_GlobalDimensions.size() == 0)
+        {
+            throw std::invalid_argument(
+                "Variable.SetMemorySelection() is an invalid "
+                "call for single value variables\n");
+        }
+        if (m_GlobalDimensions.size() != sel.m_Count.size())
+        {
+            throw std::invalid_argument(
+                "Variable.SetMemorySelection() bounding box "
+                "dimension must equal the global "
+                "dimension of the variable\n");
+        }
+
+        ConvertUint64VectorToSizetVector(sel.m_Count, m_MemoryDimensions);
+        ConvertUint64VectorToSizetVector(sel.m_Start, m_MemoryOffsets);
+    }
+
     // protected: off for now
 
     Dims m_Dimensions;       ///< array of local dimensions
     Dims m_GlobalDimensions; ///< array of global dimensions
     Dims m_GlobalOffsets;    ///< array of global offsets
+    Dims m_MemoryDimensions; ///< array of memory dimensions
+    Dims m_MemoryOffsets;    ///< array of memory offsets
     const bool m_DebugMode = false;
 
     std::string GetDimensionAsString() { return dimsToString(m_Dimensions); }
diff --git a/include/engine/adios1/ADIOS1Reader.h b/include/engine/adios1/ADIOS1Reader.h
index 22e2984765bac022d57ba63ba1b6c4b30906bd56..64566ec4edbdebda353e531560f2857ccbf7e45f 100644
--- a/include/engine/adios1/ADIOS1Reader.h
+++ b/include/engine/adios1/ADIOS1Reader.h
@@ -10,8 +10,8 @@
  *      Author: pnb
  */
 
-#ifndef BPFILEREADER_H_
-#define BPFILEREADER_H_
+#ifndef ADIOS1READER_H_
+#define ADIOS1READER_H_
 
 #include <iostream> //this must go away
 
@@ -23,7 +23,12 @@
 namespace adios
 {
 
-class BPFileReader : public Engine
+#ifdef ADIOS_NOMPI
+#define _NOMPI 1
+#endif
+#include "adios_read_v2.h" // this is adios 1.x header file
+
+class ADIOS1Reader : public Engine
 {
 
 public:
@@ -38,13 +43,13 @@ public:
      * @param debugMode
      * @param hostLanguage
      */
-    BPFileReader(ADIOS &adios, const std::string name,
+    ADIOS1Reader(ADIOS &adios, const std::string name,
                  const std::string accessMode, MPI_Comm mpiComm,
                  const Method &method, const IOMode iomode,
                  const float timeout_sec, const bool debugMode = false,
                  const unsigned int nthreads = 1);
 
-    ~BPFileReader();
+    ~ADIOS1Reader();
 
     Variable<void> *InquireVariable(const std::string name,
                                     const bool readIn = true);
@@ -93,26 +98,14 @@ public:
     void Close(const int transportIndex = -1);
 
 private:
-    capsule::STLVector
-        m_Buffer; ///< heap capsule, contains data and metadata buffers
-    // format::BP1Writer m_BP1Writer; ///< format object will provide the
-    // required
-    // BP functionality to be applied on m_Buffer and m_Transports
-
-    void Init(); ///< calls InitCapsules and InitTransports based on Method,
-                 /// called from constructor
-    void InitCapsules();
-    void InitTransports(); ///< from Transports
-
-    std::string
-    GetMdtmParameter(const std::string parameter,
-                     const std::map<std::string, std::string> &mdtmParameters);
+    void Init(); ///< called from constructor, gets the selected ADIOS1
+                 /// transport method from settings
 
     template <class T>
     Variable<T> *InquireVariableCommon(const std::string name,
                                        const bool readIn)
     {
-        std::cout << "Hello BPReaderCommon\n";
+        std::cout << "Hello ADIOS1Reader::InquireVariableCommon\n";
 
         // here read variable metadata (dimensions, type, etc.)...then create a
         // Variable like below:
@@ -121,8 +114,10 @@ private:
         // return &variable; //return address if success
         return nullptr; // on failure
     }
+
+    enum ADIOS_READ_METHOD read_method = ADIOS_READ_METHOD_BP;
 };
 
 } // end namespace adios
 
-#endif /* BPFILEREADER_H_ */
+#endif /* ADIOS1READER_H_ */
diff --git a/include/external/adios_selection.h b/include/external/adios_selection.h
new file mode 100644
index 0000000000000000000000000000000000000000..551d72ee5f8ea6297f5367e12b3759abdb6fdb1a
--- /dev/null
+++ b/include/external/adios_selection.h
@@ -0,0 +1,240 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ *
+ */
+
+/*
+ *   Streaming/Chunking/Selection Read API in C for ADIOS BP format
+ *
+ *   A SELECTION is the data ranges resulting from a QUERY over a file and
+ * variable(s).
+ *
+ *   A SELECTION can be a list of bounding boxes and point-sets. Other data
+ * structures
+ *   are not supported. Any query will result in such a selection.
+ *   Other selections are the write-block and auto.
+ *
+ *   Write block is a block of data written
+ *   by a writer process, it is identified by an index. If each writer outputs
+ * one block
+ *   then the index equals to the rank of the write process. With multi-var
+ * writing and
+ *   multiple steps in a file, index runs from 0 as rank 0 process' first block.
+ *
+ *   Auto selection lets the read method to automatically choose what to return.
+ * It will
+ *   be a block / blocks of selected writers.
+ *
+ *   If a query is a simple bounding box, the selection is the bounding box
+ * itself, so
+ *   the application does not need to retrieve the selection to work on the read
+ * data.
+ */
+#ifndef __ADIOS_SELECTION_C_H__
+#define __ADIOS_SELECTION_C_H__
+
+#include <stdint.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/*************************/
+/* Types used in the API */
+/*************************/
+
+typedef struct ADIOS_SELECTION_STRUCT ADIOS_SELECTION;
+
+/* Type of selection */
+enum ADIOS_SELECTION_TYPE
+{
+    ADIOS_SELECTION_BOUNDINGBOX = 0, /* Contiguous block of data defined by
+                                        offsets and counts in each dimension */
+    ADIOS_SELECTION_POINTS = 1,      /* List of individual points */
+    ADIOS_SELECTION_WRITEBLOCK =
+        2, /* Selection of an individual block written by a writer process */
+    ADIOS_SELECTION_AUTO = 3 /* Let the method decide what to return */
+};
+
+/* A Bounding Box */
+typedef struct
+{
+    int ndim;
+    uint64_t *start;
+    uint64_t *count;
+} ADIOS_SELECTION_BOUNDINGBOX_STRUCT;
+
+/* A list of points.
+ * It is a 1D array of indices, linearized for all dimension
+ *     (e.g.  [i1,j1,k1,i2,j2,k2,...,in,jn,kn] for n points in a 3D space.
+ * If a container selection is given, points are relative coordinates/offsets in
+ * the
+ * container box/writeblock.
+ * 1D offsets in N-dimensional container are allowed. Such selections are
+ * returned by
+ * FASTBIT and ALACRITY query method. File reading is supported for such
+ * selections.
+ * adios_selection_points_1DtoND() can be used to convert 1D to N-D points.
+ */
+typedef struct
+{
+    int ndim;
+    int _free_points_on_delete; // user provided points are not copied, won't
+                                // free either
+    uint64_t npoints;
+    uint64_t *points;
+    ADIOS_SELECTION
+    *container_selection; // a writeblock, a bounding box, or NULL
+} ADIOS_SELECTION_POINTS_STRUCT;
+
+/* A selected block produced by a writer
+ * Identified with an index in current versions.
+ */
+typedef struct
+{
+    int index;
+
+    /* NCSU ALACRITY-ADIOS:
+     *     Adding timestep-relative vs. absolute writeblock selections, as
+     *     well as sub-PG selection support. Both of these are currently only
+     *     used by the transform layer
+     */
+    int is_absolute_index; /* 0 if 'index' is relative to the current timestep,
+                              != 0
+                              otherwise (i.e., absolute index) */
+    int is_sub_pg_selection; /* Whether this writeblock selection contains
+                                sub-PG bounds.
+                                The following fields only matter if this is != 0
+                                */
+
+    /* Reads the linear range of elements in [element_offset, element_offset +
+     * nelements) */
+    uint64_t element_offset;
+    uint64_t nelements;
+} ADIOS_SELECTION_WRITEBLOCK_STRUCT;
+
+/* Let the read method decide what to return to each reading client.
+ * Hints are method-dependent parameters to influence what and how to
+ * return (e.g. the ordering of returned chunks, decomposition among
+ * read processes, etc.)
+ */
+typedef struct
+{
+    char *hints;
+} ADIOS_SELECTION_AUTO_STRUCT;
+
+/** Selection for reading a subset of a variable.
+ *   A selection is an additive list of bounding boxes and point-sets
+ */
+struct ADIOS_SELECTION_STRUCT
+{
+    enum ADIOS_SELECTION_TYPE type; /* Type of selection */
+    union {
+        ADIOS_SELECTION_BOUNDINGBOX_STRUCT bb;
+        ADIOS_SELECTION_POINTS_STRUCT points;
+        ADIOS_SELECTION_WRITEBLOCK_STRUCT block;
+        ADIOS_SELECTION_AUTO_STRUCT autosel;
+    } u;
+    // ADIOS_SELECTION             *next;
+};
+
+#ifndef __INCLUDED_FROM_FORTRAN_API__
+
+/** Boundingbox selection to read a subset of a non-scalar variable.
+ *  IN:
+ *       ndim      Number of dimensions
+ *       start     array of offsets to start reading in each dimension
+ *       count     number of data elements to read in each dimension
+ *  RETURN:        A selection which can be used to read variables
+ */
+ADIOS_SELECTION *adios_selection_boundingbox(int ndim, const uint64_t *start,
+                                             const uint64_t *count);
+
+/** Selection for a selection of an enumeration of positions.
+ *  IN:
+ *       ndim      Number of dimensions
+ *       npoints   Number of points of the selection
+ *       points    1D array of indices, compacted for all dimension
+ *                 (e.g.  [i1,j1,k1,i2,j2,k2,...,in,jn,kn] for
+ *                 n points in a 3D space.
+ */
+ADIOS_SELECTION *adios_selection_points(int ndim, uint64_t npoints,
+                                        const uint64_t *points);
+
+/** Selection for a block of data coming from a certain producer.
+ *
+ *  IN:
+ *       index      Identifier of the written block, starting from 0 for the
+ * first block
+ *                  written by producer rank 0. If each writer outputs one block
+ *                  then the index equals to the rank of the write process.
+ *                  With multi-var writing and multiple steps in a file, index
+ * should be
+ *                  calculated by the reading application using outside
+ * information beyond
+ *                  what is provided by the ADIOS Read API.
+ */
+ADIOS_SELECTION *adios_selection_writeblock(int index);
+
+/** Let the method decide what data gets to what reader process.
+ *  This selection enables each reading method to provide an 'optimal'
+ *  data transfer from writers to readers. It depends on the method and the
+ *  circumstances, what this selection actually means.
+ *
+ *  E.g. in situ processing: readers on a compute node will receive all data
+ *       from the writers on the same compute node.
+ *
+ *  IN:
+ *       hints    Method dependent parameters to influence what and how to
+ *                return (e.g. decomposition; ordering of returned chunks)
+ */
+ADIOS_SELECTION *adios_selection_auto(char *hints);
+
+/** Make a strided hyperslab selection the same way as in HDF5.
+ *  IN:
+ *       ndim      Number of dimentsions
+ *       start     array of offsets to start reading in each dimension
+ *       strides   striding steps, NULL=1 in all dimensions (= boundingbox)
+ *       count     number of data elements to read in each dimension
+ *       blocks    block size at each stride, NULL=1 in all dimensions
+ */
+/*
+   No support: Klasky, Podhorszki
+   Support:
+
+ADIOS_SELECTION* adios_selection_hyperslab (uint64_t ndim, uint64_t *start,
+uint64_t *strides,
+                                    uint64_t *count, uint64_t *blocks);
+*/
+
+/** Delete a selection and free up memory used by the selection.
+  * IN: selection
+  * RESULT: None
+  * The ADIOS_SELECTION object can be simply freed by free(), too.
+  */
+void adios_selection_delete(ADIOS_SELECTION *selection);
+
+/* Convert one selection of 1D point offsets in a bounding box,
+ * returned by FASTBIT and ALACRITY query methods, to N-dimensional points.
+ * This function works only if there is a bounding box in
+ * pointsinbox1D->u.points.container!
+ * It allocates memory for the result selection, after which the original can be
+ * freed.
+ * Return:
+ * If global==0, the points will be relative to the container, if not, the
+ * points will be
+ * global coordinates (container's starting offsets added to each point) and
+ * result's container
+ * will be NULL.
+ */
+ADIOS_SELECTION *adios_selection_points_1DtoND(ADIOS_SELECTION *pointsinbox1D,
+                                               int global);
+
+#endif /*__INCLUDED_FROM_FORTRAN_API__*/
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /*__ADIOS_SELECTION_C_H__*/
diff --git a/include/functions/adiosFunctions.h b/include/functions/adiosFunctions.h
index ab6edba1df018dfd6a17d5b740a6fabcdf8574b1..4f33c22675b8ee7072f0c4917785e6fc1bfb6311 100644
--- a/include/functions/adiosFunctions.h
+++ b/include/functions/adiosFunctions.h
@@ -182,6 +182,12 @@ BuildParametersMap(const std::vector<std::string> &parameters,
  */
 std::vector<int> CSVToVectorInt(const std::string csv);
 
+/** Convert a vector of uint64_t elements to a vector of std::size_t elements
+ *  @param input vector of uint64_t elements
+ *  @param output vector of std::size_t elements
+ */
+void ConvertUint64VectorToSizetVector(const std::vector<std::uint64_t> &in,
+                                      std::vector<std::size_t> &out);
 /**
  * Common strategy to check for heap buffer allocation for data and metadata
  * typically calculated in Write
@@ -190,7 +196,8 @@ std::vector<int> CSVToVectorInt(const std::string csv);
  * buffers ( default = 1.5 )
  * @param maxBufferSize user provided maximum buffer size
  * @param buffer to be reallocated
- * @return true: must do a transport flush, false: buffer sizes are enough to
+ * @return true: must do a transport flush, false: buffer sizes are enough
+ * to
  * contain incoming data, no need for transport flush
  */
 bool CheckBufferAllocation(const std::size_t newSize, const float growthFactor,
diff --git a/include/selection/Selection.h b/include/selection/Selection.h
new file mode 100644
index 0000000000000000000000000000000000000000..70d4c831409cb0e1cd7beeee0e121470acf39d1f
--- /dev/null
+++ b/include/selection/Selection.h
@@ -0,0 +1,70 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ */
+
+/*
+ *   Selection API in C++
+ *
+ *   A SELECTION is the data ranges resulting from a QUERY over a file and
+ * variable(s).
+ *
+ *   A SELECTION can be a list of bounding boxes and point-sets. Other data
+ * structures
+ *   are not supported. Any query will result in such a selection.
+ *   Other selections are the write-block and auto.
+ *
+ *   Write block is a block of data written
+ *   by a writer process, it is identified by an index. If each writer outputs
+ * one block
+ *   then the index equals to the rank of the write process. With multi-var
+ * writing and
+ *   multiple steps in a file, index runs from 0 as rank 0 process' first block.
+ *
+ *   Auto selection lets the read method to automatically choose what to return.
+ * It will
+ *   be a block / blocks of selected writers.
+ *
+ *   If a query is a simple bounding box, the selection is the bounding box
+ * itself, so
+ *   the application does not need to retrieve the selection to work on the read
+ * data.
+ */
+#ifndef __ADIOS_SELECTION_H__
+#define __ADIOS_SELECTION_H__
+
+/// \cond EXCLUDE_FROM_DOXYGEN
+#include "external/adios_selection.h"
+#include <stdint.h>
+/// \endcond
+
+namespace adios
+{
+
+/*************************/
+/* Types used in the API */
+/*************************/
+/* Type of selection */
+enum class SelectionType
+{
+    // Contiguous block of data defined by offsets and counts in each
+    // dimension
+    BoundingBox = ADIOS_SELECTION_BOUNDINGBOX,
+    // List of individual points
+    Points = ADIOS_SELECTION_POINTS,
+    // Selection of an individual block written by a writer process
+    WriteBlock = ADIOS_SELECTION_WRITEBLOCK,
+    // Let the method decide what to return
+    Auto = ADIOS_SELECTION_AUTO
+};
+
+class Selection
+{
+public:
+    Selection(const SelectionType t) : m_Type(t){};
+    const SelectionType m_Type;
+};
+
+} // namespace adios
+
+#endif /*__ADIOS_SELECTION_H__*/
diff --git a/include/selection/SelectionBoundingBox.h b/include/selection/SelectionBoundingBox.h
new file mode 100644
index 0000000000000000000000000000000000000000..b110fd96e517a2ee7854db1bad92d422dfd3d5e1
--- /dev/null
+++ b/include/selection/SelectionBoundingBox.h
@@ -0,0 +1,38 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ */
+
+#ifndef __ADIOS_SELECTION_BOUNDINGBOX_H__
+#define __ADIOS_SELECTION_BOUNDINGBOX_H__
+
+/// \cond EXCLUDE_FROM_DOXYGEN
+#include <cstdint>
+/// \endcond
+
+#include "selection/Selection.h"
+
+namespace adios
+{
+
+/** Boundingbox selection to read a subset of a non-scalar variable.
+ *  @param start     array of offsets to start reading in each dimension
+ *  @param count     number of data elements to read in each dimension
+ */
+class SelectionBoundingBox : public Selection
+{
+public:
+    SelectionBoundingBox(const std::vector<std::uint64_t> start,
+                         const std::vector<std::uint64_t> count)
+    : Selection(SelectionType::BoundingBox), m_Start(start), m_Count(count)
+    {
+    }
+    ~SelectionBoundingBox(){};
+
+    std::vector<std::uint64_t> m_Start;
+    std::vector<std::uint64_t> m_Count;
+};
+
+} // namespace adios
+
+#endif /*__ADIOS_SELECTION_BOUNDINGBOX_H__*/
diff --git a/include/selection/SelectionPoints.h b/include/selection/SelectionPoints.h
new file mode 100644
index 0000000000000000000000000000000000000000..13fa951cbaa587c2f1592e64dd9eeb46601d29cd
--- /dev/null
+++ b/include/selection/SelectionPoints.h
@@ -0,0 +1,55 @@
+/*
+ * Distributed under the OSI-approved Apache License, Version 2.0.  See
+ * accompanying file Copyright.txt for details.
+ */
+
+#ifndef __ADIOS_SELECTION_POINTS_H__
+#define __ADIOS_SELECTION_POINTS_H__
+
+/// \cond EXCLUDE_FROM_DOXYGEN
+#include <cstdint>
+/// \endcond
+
+#include "selection/Selection.h"
+#include "selection/SelectionBoundingBox.h"
+
+namespace adios
+{
+
+/** Selection for a selection of an enumeration of positions.
+ *  @param     ndim      Number of dimensions
+ *  @param     npoints   Number of points of the selection
+ *  @param     points    1D array of indices, compacted for all dimension
+ *              (e.g.  [i1,j1,k1,i2,j2,k2,...,in,jn,kn] for
+ *              n points in a 3D space.
+ */
+class SelectionPoints : public Selection
+{
+public:
+    SelectionPoints(std::size_t ndim, std::size_t npoints,
+                    std::vector<std::uint64_t> &points)
+    : Selection(SelectionType::Points), m_Ndim(ndim), m_Npoints(npoints),
+      m_Points(points)
+    {
+    }
+
+    ///< C-style constructor to be used in the C-to-C++ wrapper
+    SelectionPoints(std::size_t ndim, std::size_t npoints, uint64_t *points)
+    : Selection(SelectionType::Points), m_Ndim(ndim), m_Npoints(npoints),
+      m_Points(std::vector<std::uint64_t>()), m_PointsC(points)
+    {
+    }
+
+    ~SelectionPoints(){};
+
+    const std::size_t m_Ndim;
+    const std::size_t m_Npoints;
+    std::vector<std::uint64_t> &m_Points;
+    ///< C-to-C++ wrapper needs a pointer to hold the points created by the C
+    /// application
+    std::uint64_t *m_PointsC = nullptr;
+};
+
+} // namespace adios
+
+#endif /*__ADIOS_SELECTION_POINTS_H__*/
diff --git a/source/CMakeLists.txt b/source/CMakeLists.txt
index 1b3472a4020d6a4cfea8858aea614bb1a04b24b5..d3340d88ae711916eb5b02d6fef3173c3533abf3 100644
--- a/source/CMakeLists.txt
+++ b/source/CMakeLists.txt
@@ -79,4 +79,34 @@ if(ADIOS_USE_MPI)
   target_include_directories(adios2 PUBLIC ${MPI_C_INCLUDE_PATH})
   target_compile_definitions(adios2 PUBLIC ADIOS_HAVE_MPI)
   target_link_libraries(adios2 PUBLIC ${MPI_C_LIBRARIES})
+else()
+  target_sources(adios2 PRIVATE mpidummy.cpp)
+endif()
+
+if(ADIOS_USE_ADIOS1)
+  find_package(ADIOS1 REQUIRED)
+  target_sources(adios2 PRIVATE
+    engine/adios1/ADIOS1Reader.cpp
+    engine/adios1/ADIOS1Writer.cpp
+  )
+  target_compile_definitions(adios2 PRIVATE ADIOS_HAVE_ADIOS1)
+  target_link_libraries(adios2 PRIVATE adios1::adios)
+endif()
+
+if(ADIOS_USE_DataMan)
+  find_package(DataMan REQUIRED)
+  target_sources(adios2 PRIVATE
+    engine/dataman/DataManReader.cpp
+    engine/dataman/DataManWriter.cpp
+    transport/wan/MdtmMan.cpp
+  )
+  target_compile_definitions(adios2 PRIVATE ADIOS_HAVE_DATAMAN)
+  target_link_libraries(adios2 PRIVATE DataMan::DataMan)
+endif()
+
+if(ADIOS_USE_BZip2)
+  find_package(BZip2 REQUIRED)
+  target_sources(adios2 PRIVATE transform/BZip2.cpp)
+  target_compile_definitions(adios2 PRIVATE ADIOS_HAVE_BZIP2)
+  target_link_libraries(adios2 PRIVATE BZip2::BZip2)
 endif()
diff --git a/source/engine/adios1/ADIOS1Reader.cpp b/source/engine/adios1/ADIOS1Reader.cpp
index e3ff93ec01d049bebf8e00c5a03485cc85ef5c2a..6f8fd564a959a147fe436a0f888651fe0ba8bac8 100644
--- a/source/engine/adios1/ADIOS1Reader.cpp
+++ b/source/engine/adios1/ADIOS1Reader.cpp
@@ -2,224 +2,165 @@
  * Distributed under the OSI-approved Apache License, Version 2.0.  See
  * accompanying file Copyright.txt for details.
  *
- * BPFileReader.cpp
+ * ADIOS1Reader.cpp
  *
  *  Created on: Feb 27, 2017
  *      Author: wfg
  */
 
-#include "engine/bp/BPFileReader.h"
+#include "engine/adios1/ADIOS1Reader.h"
+#include "ADIOS.h"
 
-#include "core/Support.h"
-#include "functions/adiosFunctions.h"      //CSVToVector
-#include "transport/file/FileDescriptor.h" // uses POSIX
-#include "transport/file/FilePointer.h"    // uses C FILE*
-
-// supported transports
-#include "transport/file/FStream.h" // uses C++ fstream
+extern int adios_verbose_level;
+extern int adios_errno;
 
 namespace adios
 {
 
-BPFileReader::BPFileReader(ADIOS &adios, const std::string name,
+ADIOS1Reader::ADIOS1Reader(ADIOS &adios, const std::string name,
                            const std::string accessMode, MPI_Comm mpiComm,
                            const Method &method, const IOMode iomode,
                            const float timeout_sec, const bool debugMode,
                            const unsigned int nthreads)
-: Engine(adios, "BPFileReader", name, accessMode, mpiComm, method, debugMode,
-         nthreads, " BPFileReader constructor (or call to ADIOS Open).\n"),
-  m_Buffer(accessMode, m_RankMPI, m_DebugMode)
+: Engine(adios, "ADIOS1Reader", name, accessMode, mpiComm, method, debugMode,
+         nthreads, " ADIOS1Reader constructor (or call to ADIOS Open).\n")
 {
     Init();
+    adios_read_init_method(read_method, m_MPIComm, "");
 }
 
-BPFileReader::~BPFileReader() {}
+ADIOS1Reader::~ADIOS1Reader() { adios_read_finalize_method(read_method); }
 
 Variable<void> *
-BPFileReader::InquireVariable(const std::string name,
+ADIOS1Reader::InquireVariable(const std::string name,
                               const bool readIn) // not yet implemented
 {
     return nullptr;
 }
 
-Variable<char> *BPFileReader::InquireVariableChar(const std::string name,
+Variable<char> *ADIOS1Reader::InquireVariableChar(const std::string name,
                                                   const bool readIn)
 {
     return InquireVariableCommon<char>(name, readIn);
 }
 
 Variable<unsigned char> *
-BPFileReader::InquireVariableUChar(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableUChar(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<unsigned char>(name, readIn);
 }
 
-Variable<short> *BPFileReader::InquireVariableShort(const std::string name,
+Variable<short> *ADIOS1Reader::InquireVariableShort(const std::string name,
                                                     const bool readIn)
 {
     return InquireVariableCommon<short>(name, readIn);
 }
 
 Variable<unsigned short> *
-BPFileReader::InquireVariableUShort(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableUShort(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<unsigned short>(name, readIn);
 }
 
-Variable<int> *BPFileReader::InquireVariableInt(const std::string name,
+Variable<int> *ADIOS1Reader::InquireVariableInt(const std::string name,
                                                 const bool readIn)
 {
     return InquireVariableCommon<int>(name, readIn);
 }
 
 Variable<unsigned int> *
-BPFileReader::InquireVariableUInt(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableUInt(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<unsigned int>(name, readIn);
 }
 
-Variable<long int> *BPFileReader::InquireVariableLInt(const std::string name,
+Variable<long int> *ADIOS1Reader::InquireVariableLInt(const std::string name,
                                                       const bool readIn)
 {
     return InquireVariableCommon<long int>(name, readIn);
 }
 
 Variable<unsigned long int> *
-BPFileReader::InquireVariableULInt(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableULInt(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<unsigned long int>(name, readIn);
 }
 
 Variable<long long int> *
-BPFileReader::InquireVariableLLInt(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableLLInt(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<long long int>(name, readIn);
 }
 
 Variable<unsigned long long int> *
-BPFileReader::InquireVariableULLInt(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableULLInt(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<unsigned long long int>(name, readIn);
 }
 
-Variable<float> *BPFileReader::InquireVariableFloat(const std::string name,
+Variable<float> *ADIOS1Reader::InquireVariableFloat(const std::string name,
                                                     const bool readIn)
 {
     return InquireVariableCommon<float>(name, readIn);
 }
 
-Variable<double> *BPFileReader::InquireVariableDouble(const std::string name,
+Variable<double> *ADIOS1Reader::InquireVariableDouble(const std::string name,
                                                       const bool readIn)
 {
     return InquireVariableCommon<double>(name, readIn);
 }
 
 Variable<long double> *
-BPFileReader::InquireVariableLDouble(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableLDouble(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<long double>(name, readIn);
 }
 
 Variable<std::complex<float>> *
-BPFileReader::InquireVariableCFloat(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableCFloat(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<std::complex<float>>(name, readIn);
 }
 
 Variable<std::complex<double>> *
-BPFileReader::InquireVariableCDouble(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableCDouble(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<std::complex<double>>(name, readIn);
 }
 
 Variable<std::complex<long double>> *
-BPFileReader::InquireVariableCLDouble(const std::string name, const bool readIn)
+ADIOS1Reader::InquireVariableCLDouble(const std::string name, const bool readIn)
 {
     return InquireVariableCommon<std::complex<long double>>(name, readIn);
 }
 
-VariableCompound *BPFileReader::InquireVariableCompound(const std::string name,
+VariableCompound *ADIOS1Reader::InquireVariableCompound(const std::string name,
                                                         const bool readIn)
 {
     return nullptr;
 }
 
-void BPFileReader::Close(const int transportIndex) {}
+void ADIOS1Reader::Close(const int transportIndex) {}
 
 // PRIVATE
-void BPFileReader::Init()
+void ADIOS1Reader::Init()
 {
     if (m_DebugMode == true)
     {
         if (m_AccessMode != "r" && m_AccessMode != "read")
             throw std::invalid_argument(
-                "ERROR: BPFileReader doesn't support access mode " +
+                "ERROR: ADIOS1Reader doesn't support access mode " +
                 m_AccessMode +
-                ", in call to ADIOS Open or BPFileReader constructor\n");
-    }
-
-    InitCapsules();
-    InitTransports();
-}
-
-void BPFileReader::InitCapsules()
-{
-    // here init memory capsules
-}
-
-void BPFileReader::InitTransports() // maybe move this?
-{
-    if (m_DebugMode == true)
-    {
-        if (TransportNamesUniqueness() == false)
-        {
-            throw std::invalid_argument(
-                "ERROR: two transports of the same kind (e.g file IO) "
-                "can't have the same name, modify with name= in Method "
-                "AddTransport\n");
-        }
+                ", in call to ADIOS Open or ADIOS1Reader constructor\n");
     }
 
     for (const auto &parameters : m_Method.m_TransportParameters)
     {
         auto itTransport = parameters.find("transport");
-        if (itTransport->second == "file" || itTransport->second == "File")
+        if (itTransport->second == "file" || itTransport->second == "File" ||
+            itTransport->second == "bp" || itTransport->second == "BP")
         {
-            auto itLibrary = parameters.find("library");
-            if (itLibrary == parameters.end() ||
-                itLibrary->second == "POSIX") // use default POSIX
-            {
-                auto file = std::make_shared<transport::FileDescriptor>(
-                    m_MPIComm, m_DebugMode);
-                // m_BP1Reader.OpenRankFiles( m_Name, m_AccessMode, *file );
-                m_Transports.push_back(std::move(file));
-            }
-            else if (itLibrary->second == "FILE*" ||
-                     itLibrary->second == "stdio.h")
-            {
-                auto file = std::make_shared<transport::FilePointer>(
-                    m_MPIComm, m_DebugMode);
-                // m_BP1Reader.OpenRankFiles( m_Name, m_AccessMode, *file );
-                m_Transports.push_back(std::move(file));
-            }
-            else if (itLibrary->second == "fstream" ||
-                     itLibrary->second == "std::fstream")
-            {
-                auto file = std::make_shared<transport::FStream>(m_MPIComm,
-                                                                 m_DebugMode);
-                // m_BP1Reader.OpenRankFiles( m_Name, m_AccessMode, *file );
-                m_Transports.push_back(std::move(file));
-            }
-            else if (itLibrary->second == "MPI-IO")
-            {
-            }
-            else
-            {
-                if (m_DebugMode == true)
-                    throw std::invalid_argument(
-                        "ERROR: file transport library " + itLibrary->second +
-                        " not supported, in " + m_Name + m_EndMessage);
-            }
+            read_method = ADIOS_READ_METHOD_BP;
         }
         else
         {
diff --git a/source/functions/adiosFunctions.cpp b/source/functions/adiosFunctions.cpp
index f2d703b5b09c82f8f3775669ebdf8952d90e1d51..032d3aeb6238c0d8bfd0abe324971b465f49b8fe 100644
--- a/source/functions/adiosFunctions.cpp
+++ b/source/functions/adiosFunctions.cpp
@@ -633,6 +633,17 @@ std::vector<int> CSVToVectorInt(const std::string csv)
     return numbers;
 }
 
+void ConvertUint64VectorToSizetVector(const std::vector<std::uint64_t> &in,
+                                      std::vector<std::size_t> &out)
+{
+    out.clear();
+    out.reserve(in.size());
+    for (const auto inElement : in)
+    {
+        out.push_back(static_cast<std::size_t>(inElement));
+    }
+}
+
 bool CheckBufferAllocation(const std::size_t newSize, const float growthFactor,
                            const std::size_t maxBufferSize,
                            std::vector<char> &buffer)