You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ignite.apache.org by sb...@apache.org on 2017/02/15 10:44:58 UTC

[33/50] [abbrv] ignite git commit: IGNITE-1680: CPP: Implemented API for user entry point lookup. This closes #1430.

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core-test/src/cache_invoke_test.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core-test/src/cache_invoke_test.cpp b/modules/platforms/cpp/core-test/src/cache_invoke_test.cpp
new file mode 100644
index 0000000..3ab6f2b9
--- /dev/null
+++ b/modules/platforms/cpp/core-test/src/cache_invoke_test.cpp
@@ -0,0 +1,553 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _MSC_VER
+    #define BOOST_TEST_DYN_LINK
+#endif
+
+#include <sstream>
+#include <algorithm>
+
+#include <boost/test/unit_test.hpp>
+
+#include "ignite/common/utils.h"
+#include "ignite/ignite.h"
+#include "ignite/ignition.h"
+
+#include "ignite/ignite_binding_context.h"
+#include "ignite/cache/cache_entry_processor.h"
+
+using namespace boost::unit_test;
+
+using namespace ignite;
+using namespace ignite::cache;
+using namespace ignite::common;
+
+/**
+ * CacheEntryModifier class for invoke tests.
+ */
+class CacheEntryModifier : public CacheEntryProcessor<CacheEntryModifier, int, int, int, int>
+{
+public:
+    /**
+     * Constructor.
+     */
+    CacheEntryModifier() : num(0)
+    {
+        // No-op.
+    }
+
+    /**
+     * Constructor.
+     *
+     * @param num Number to substract from the entry.
+     */
+    CacheEntryModifier(int num) : num(num)
+    {
+        // No-op.
+    }
+
+    /**
+     * Copy constructor.
+     *
+     * @param other Other instance.
+     */
+    CacheEntryModifier(const CacheEntryModifier& other) : num(other.num)
+    {
+        // No-op.
+    }
+
+    /**
+     * Assignment operator.
+     *
+     * @param other Other instance.
+     * @return This instance.
+     */
+    CacheEntryModifier& operator=(const CacheEntryModifier& other)
+    {
+        num = other.num;
+
+        return *this;
+    }
+
+    /**
+     * Call instance.
+     *
+     * @return New value of entry multiplied by two.
+     */
+    virtual int Process(MutableCacheEntry<int, int>& entry, const int& arg)
+    {
+        if (entry.IsExists())
+            entry.SetValue(entry.GetValue() - arg - num);
+        else
+            entry.SetValue(42);
+
+        return entry.GetValue() * 2;
+    }
+
+    /**
+     * Get number.
+     *
+     * @return Number to substract from entry value.
+     */
+    int GetNum() const
+    {
+        return num;
+    }
+
+private:
+    /** Number to substract. */
+    int num;
+};
+
+namespace ignite
+{
+    namespace binary
+    {
+        /**
+         * Binary type definition for CacheEntryModifier.
+         */
+        IGNITE_BINARY_TYPE_START(CacheEntryModifier)
+            IGNITE_BINARY_GET_TYPE_ID_AS_HASH(CacheEntryModifier)
+            IGNITE_BINARY_GET_TYPE_NAME_AS_IS(CacheEntryModifier)
+            IGNITE_BINARY_GET_FIELD_ID_AS_HASH
+            IGNITE_BINARY_GET_HASH_CODE_ZERO(CacheEntryModifier)
+            IGNITE_BINARY_IS_NULL_FALSE(CacheEntryModifier)
+            IGNITE_BINARY_GET_NULL_DEFAULT_CTOR(CacheEntryModifier)
+
+            void Write(BinaryWriter& writer, CacheEntryModifier obj)
+            {
+                writer.WriteInt32("num", obj.GetNum());
+            }
+
+            CacheEntryModifier Read(BinaryReader& reader)
+            {
+                int num = reader.ReadInt32("num");
+
+                return CacheEntryModifier(num);
+            }
+        IGNITE_BINARY_TYPE_END
+    }
+}
+
+/**
+ * Divisor class for invoke tests.
+ */
+class Divisor : public CacheEntryProcessor<Divisor, int, int, double, double>
+{
+public:
+    /**
+     * Constructor.
+     */
+    Divisor() : scale(1.0)
+    {
+        // No-op.
+    }
+
+    /**
+     * Constructor.
+     *
+     * @param scale Scale.
+     */
+    Divisor(double scale) : scale(scale)
+    {
+        // No-op.
+    }
+
+    /**
+     * Copy constructor.
+     *
+     * @param other Other instance.
+     */
+    Divisor(const Divisor& other) : scale(other.scale)
+    {
+        // No-op.
+    }
+
+    /**
+     * Assignment operator.
+     *
+     * @param other Other instance.
+     * @return This instance.
+     */
+    Divisor& operator=(const Divisor& other)
+    {
+        scale = other.scale;
+
+        return *this;
+    }
+
+    /**
+     * Call instance.
+     *
+     * @return New value before cast to int.
+     */
+    virtual double Process(MutableCacheEntry<int, int>& entry, const double& arg)
+    {
+        double res = 0.0;
+
+        if (entry.IsExists())
+        {
+            res = (entry.GetValue() / arg) * scale;
+
+            entry.SetValue(static_cast<int>(res));
+        }
+
+        return res;
+    }
+
+    /**
+     * Get scale.
+     *
+     * @return Scale.
+     */
+    double GetScale() const
+    {
+        return scale;
+    }
+
+private:
+    /** Scale. */
+    double scale;
+};
+
+namespace ignite
+{
+    namespace binary
+    {
+        /**
+         * Binary type definition for Divisor.
+         */
+        IGNITE_BINARY_TYPE_START(Divisor)
+            IGNITE_BINARY_GET_TYPE_ID_AS_HASH(Divisor)
+            IGNITE_BINARY_GET_TYPE_NAME_AS_IS(Divisor)
+            IGNITE_BINARY_GET_FIELD_ID_AS_HASH
+            IGNITE_BINARY_GET_HASH_CODE_ZERO(Divisor)
+            IGNITE_BINARY_IS_NULL_FALSE(Divisor)
+            IGNITE_BINARY_GET_NULL_DEFAULT_CTOR(Divisor)
+
+            void Write(BinaryWriter& writer, Divisor obj)
+            {
+                writer.WriteDouble("scale", obj.GetScale());
+            }
+
+            Divisor Read(BinaryReader& reader)
+            {
+                double scale = reader.ReadDouble("scale");
+
+                return Divisor(scale);
+            }
+        IGNITE_BINARY_TYPE_END
+    }
+}
+
+/**
+ * Character remover class for invoke tests.
+ */
+class CharRemover : public CacheEntryProcessor<CharRemover, std::string, std::string, int, bool>
+{
+public:
+    /**
+     * Constructor.
+     */
+    CharRemover() : toRemove(0)
+    {
+        // No-op.
+    }
+
+    /**
+     * Constructor.
+     *
+     * @param toRemove Char to remove.
+     */
+    CharRemover(char toRemove) : toRemove(toRemove)
+    {
+        // No-op.
+    }
+
+    /**
+     * Copy constructor.
+     *
+     * @param other Other instance.
+     */
+    CharRemover(const CharRemover& other) : toRemove(other.toRemove)
+    {
+        // No-op.
+    }
+
+    /**
+     * Assignment operator.
+     *
+     * @param other Other instance.
+     * @return This instance.
+     */
+    CharRemover& operator=(const CharRemover& other)
+    {
+        toRemove = other.toRemove;
+
+        return *this;
+    }
+
+    /**
+     * Call instance.
+     *
+     * @return New value before cast to int.
+     */
+    virtual int Process(MutableCacheEntry<std::string, std::string>& entry, const bool& replaceWithSpace)
+    {
+        int res = 0;
+
+        if (entry.IsExists())
+        {
+            std::string val(entry.GetValue());
+
+            res = static_cast<int>(std::count(val.begin(), val.end(), toRemove));
+
+            if (replaceWithSpace)
+                std::replace(val.begin(), val.end(), toRemove, ' ');
+            else
+                val.erase(std::remove(val.begin(), val.end(), toRemove), val.end());
+
+            if (val.empty())
+                entry.Remove();
+            else
+                entry.SetValue(val);
+        }
+
+        return res;
+    }
+
+    /**
+     * Get scale.
+     *
+     * @return Scale.
+     */
+    char GetCharToRemove() const
+    {
+        return toRemove;
+    }
+
+private:
+    /** Char to remove. */
+    char toRemove;
+};
+
+namespace ignite
+{
+    namespace binary
+    {
+        /**
+         * Binary type definition for CharRemover.
+         */
+        IGNITE_BINARY_TYPE_START(CharRemover)
+            IGNITE_BINARY_GET_TYPE_ID_AS_HASH(CharRemover)
+            IGNITE_BINARY_GET_TYPE_NAME_AS_IS(CharRemover)
+            IGNITE_BINARY_GET_FIELD_ID_AS_HASH
+            IGNITE_BINARY_GET_HASH_CODE_ZERO(CharRemover)
+            IGNITE_BINARY_IS_NULL_FALSE(CharRemover)
+            IGNITE_BINARY_GET_NULL_DEFAULT_CTOR(CharRemover)
+
+            void Write(BinaryWriter& writer, CharRemover obj)
+            {
+                writer.WriteInt8("toRemove", obj.GetCharToRemove());
+            }
+
+            CharRemover Read(BinaryReader& reader)
+            {
+                char toRemove = static_cast<char>(reader.ReadInt8("toRemove"));
+
+                return CharRemover(toRemove);
+            }
+        IGNITE_BINARY_TYPE_END
+    }
+}
+
+IGNITE_EXPORTED_CALL void IgniteModuleInit(ignite::IgniteBindingContext& context)
+{
+    IgniteBinding binding = context.GetBingding();
+
+    binding.RegisterCacheEntryProcessor<CacheEntryModifier>();
+    binding.RegisterCacheEntryProcessor<Divisor>();
+}
+
+/**
+ * Test setup fixture.
+ */
+struct CacheInvokeTestSuiteFixture {
+
+    Ignite CreateGrid()
+    {
+        IgniteConfiguration cfg;
+
+        cfg.jvmOpts.push_back("-Xdebug");
+        cfg.jvmOpts.push_back("-Xnoagent");
+        cfg.jvmOpts.push_back("-Djava.compiler=NONE");
+        cfg.jvmOpts.push_back("-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=5005");
+        cfg.jvmOpts.push_back("-XX:+HeapDumpOnOutOfMemoryError");
+        cfg.jvmOpts.push_back("-DIGNITE_ATOMIC_CACHE_DELETE_HISTORY_SIZE=1000");
+
+#ifdef IGNITE_TESTS_32
+        cfg.jvmInitMem = 256;
+        cfg.jvmMaxMem = 512;
+#else
+        cfg.jvmInitMem = 512;
+        cfg.jvmMaxMem = 2048;
+#endif
+
+        cfg.springCfgPath = std::string(getenv("IGNITE_NATIVE_TEST_CPP_CONFIG_PATH")) + "/cache-query.xml";
+
+        IgniteError err;
+
+        Ignite grid0 = Ignition::Start(cfg, &err);
+
+        if (err.GetCode() != IgniteError::IGNITE_SUCCESS)
+            BOOST_ERROR(err.GetText());
+
+        return grid0;
+    }
+
+    /**
+     * Constructor.
+     */
+    CacheInvokeTestSuiteFixture()
+    {
+        grid = CreateGrid();
+    }
+
+    /**
+     * Destructor.
+     */
+    ~CacheInvokeTestSuiteFixture()
+    {
+        Ignition::Stop(grid.GetName(), true);
+    }
+
+    Ignite grid;
+};
+
+BOOST_FIXTURE_TEST_SUITE(CacheInvokeTestSuite, CacheInvokeTestSuiteFixture)
+
+/**
+ * Test cache invoke on existing entry.
+ */
+BOOST_AUTO_TEST_CASE(TestExisting)
+{
+    Cache<int, int> cache = grid.GetOrCreateCache<int, int>("TestCache");
+
+    cache.Put(5, 20);
+
+    CacheEntryModifier ced(5);
+
+    int res = cache.Invoke<int>(5, ced, 4);
+
+    BOOST_CHECK_EQUAL(res, 22);
+
+    BOOST_CHECK_EQUAL(cache.Get(5), 11);
+}
+
+/**
+ * Test cache invoke on non-existing entry.
+ */
+BOOST_AUTO_TEST_CASE(TestNonExisting)
+{
+    Cache<int, int> cache = grid.GetOrCreateCache<int, int>("TestCache");
+
+    CacheEntryModifier ced;
+
+    int res = cache.Invoke<int>(4, ced, 4);
+
+    BOOST_CHECK_EQUAL(res, 84);
+
+    BOOST_CHECK_EQUAL(cache.Get(4), 42);
+}
+
+/**
+ * Test cache several invokes on the same entry.
+ */
+BOOST_AUTO_TEST_CASE(TestSeveral)
+{
+    Cache<int, int> cache = grid.GetOrCreateCache<int, int>("TestCache");
+
+    CacheEntryModifier ced(2);
+    Divisor div(10.0);
+
+    int res1 = cache.Invoke<int>(100, ced, 0);
+
+    BOOST_CHECK_EQUAL(res1, 84);
+
+    BOOST_CHECK_EQUAL(cache.Get(100), 42);
+
+    double res2 = cache.Invoke<double>(100, div, 200.0);
+
+    BOOST_CHECK_CLOSE(res2, 2.1, 1E-6);
+
+    BOOST_CHECK_EQUAL(cache.Get(100), 2);
+
+    res2 = cache.Invoke<double>(100, div, 3.0);
+
+    BOOST_CHECK_CLOSE(res2, 6.6666666, 1E-6);
+
+    BOOST_CHECK_EQUAL(cache.Get(100), 6);
+
+    res1 = cache.Invoke<int>(100, ced, -12);
+
+    BOOST_CHECK_EQUAL(res1, 32);
+
+    BOOST_CHECK_EQUAL(cache.Get(100), 16);
+}
+
+/**
+ * Test cache several invokes on the string entry.
+ */
+BOOST_AUTO_TEST_CASE(TestStrings)
+{
+    IgniteBinding binding = grid.GetBinding();
+
+    binding.RegisterCacheEntryProcessor<CharRemover>();
+
+    Cache<std::string, std::string> cache = grid.GetOrCreateCache<std::string, std::string>("TestCache");
+
+    CharRemover cr('.');
+
+    int res = cache.Invoke<int>("some key", cr, false);
+
+    BOOST_CHECK_EQUAL(res, 0);
+    BOOST_CHECK(!cache.ContainsKey("some key"));
+
+    cache.Put("some key", "Some.Value.Separated.By.Dots");
+
+    res = cache.Invoke<int>("some key", cr, false);
+
+    BOOST_CHECK_EQUAL(res, 4);
+    BOOST_CHECK_EQUAL(cache.Get("some key"), std::string("SomeValueSeparatedByDots"));
+
+    cache.Put("some key", "Some.Other.Weird.Value");
+
+    res = cache.Invoke<int>("some key", cr, true);
+
+    BOOST_CHECK_EQUAL(res, 3);
+    BOOST_CHECK_EQUAL(cache.Get("some key"), std::string("Some Other Weird Value"));
+
+    cache.Put("some key", "...........");
+
+    res = cache.Invoke<int>("some key", cr, false);
+
+    BOOST_CHECK_EQUAL(res, 11);
+    BOOST_CHECK(!cache.ContainsKey("some key"));
+}
+
+BOOST_AUTO_TEST_SUITE_END()

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core-test/src/cache_test.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core-test/src/cache_test.cpp b/modules/platforms/cpp/core-test/src/cache_test.cpp
index 1aa7277..f38eecc 100644
--- a/modules/platforms/cpp/core-test/src/cache_test.cpp
+++ b/modules/platforms/cpp/core-test/src/cache_test.cpp
@@ -103,11 +103,10 @@ struct CacheTestSuiteFixture {
      */
     ~CacheTestSuiteFixture()
     {
-        Ignition::Stop(grid0.GetName(), true);
-        Ignition::Stop(grid1.GetName(), true);
-
         grid0 = Ignite();
         grid1 = Ignite();
+
+        Ignition::StopAll(true);
     }
 };
 

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core-test/src/cluster_test.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core-test/src/cluster_test.cpp b/modules/platforms/cpp/core-test/src/cluster_test.cpp
new file mode 100644
index 0000000..660ff59
--- /dev/null
+++ b/modules/platforms/cpp/core-test/src/cluster_test.cpp
@@ -0,0 +1,98 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _MSC_VER
+    #define BOOST_TEST_DYN_LINK
+#endif
+
+#include <boost/test/unit_test.hpp>
+
+#include <ignite/ignition.h>
+
+using namespace ignite;
+using namespace ignite::common::concurrent;
+
+using namespace boost::unit_test;
+
+/*
+ * Test setup fixture.
+ */
+struct ClusterTestSuiteFixture {
+    /*
+     * Constructor.
+     */
+    ClusterTestSuiteFixture()
+    {
+        IgniteConfiguration cfg;
+
+        cfg.jvmOpts.push_back("-Xdebug");
+        cfg.jvmOpts.push_back("-Xnoagent");
+        cfg.jvmOpts.push_back("-Djava.compiler=NONE");
+        cfg.jvmOpts.push_back("-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=5005");
+        cfg.jvmOpts.push_back("-XX:+HeapDumpOnOutOfMemoryError");
+
+#ifdef IGNITE_TESTS_32
+        cfg.jvmInitMem = 256;
+        cfg.jvmMaxMem = 768;
+#else
+        cfg.jvmInitMem = 1024;
+        cfg.jvmMaxMem = 4096;
+#endif
+
+        cfg.springCfgPath.assign(getenv("IGNITE_NATIVE_TEST_CPP_CONFIG_PATH")).append("/cache-test.xml");
+
+        grid = Ignition::Start(cfg, "ClusterTest");
+    }
+
+    /*
+     * Destructor.
+     */
+    ~ClusterTestSuiteFixture()
+    {
+        Ignition::StopAll(true);
+        grid = Ignite();
+    }
+
+    Ignite grid;
+};
+
+BOOST_FIXTURE_TEST_SUITE(ClusterTestSuite, ClusterTestSuiteFixture)
+
+BOOST_AUTO_TEST_CASE(IgniteImplProjection)
+{
+    impl::IgniteImpl* impl = impl::IgniteImpl::GetFromProxy(grid);
+
+    BOOST_REQUIRE(impl != 0);
+    BOOST_REQUIRE(impl->GetProjection().IsValid());
+}
+
+BOOST_AUTO_TEST_CASE(IgniteImplForServers)
+{
+    impl::IgniteImpl* impl = impl::IgniteImpl::GetFromProxy(grid);
+
+    BOOST_REQUIRE(impl != 0);
+
+    SharedPointer<impl::cluster::ClusterGroupImpl> clusterGroup = impl->GetProjection();
+
+    BOOST_REQUIRE(clusterGroup.IsValid());
+
+    IgniteError err;
+
+    BOOST_REQUIRE(clusterGroup.Get()->ForServers(err).IsValid());
+}
+
+BOOST_AUTO_TEST_SUITE_END()
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core-test/src/interop_memory_test.cpp
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core-test/src/interop_memory_test.cpp b/modules/platforms/cpp/core-test/src/interop_memory_test.cpp
index 1c782b5..3abc82d 100644
--- a/modules/platforms/cpp/core-test/src/interop_memory_test.cpp
+++ b/modules/platforms/cpp/core-test/src/interop_memory_test.cpp
@@ -35,7 +35,8 @@ BOOST_AUTO_TEST_CASE(MemoryReallocationTest)
     using impl::interop::InteropMemory;
     using common::concurrent::SharedPointer;
 
-    IgniteEnvironment env;
+    IgniteConfiguration cfg;
+    IgniteEnvironment env(cfg);
 
     SharedPointer<InteropMemory> mem = env.AllocateMemory();
 

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/Makefile.am
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/Makefile.am b/modules/platforms/cpp/core/Makefile.am
index 56e0c0a..46d6bc9 100644
--- a/modules/platforms/cpp/core/Makefile.am
+++ b/modules/platforms/cpp/core/Makefile.am
@@ -67,6 +67,7 @@ libignite_la_SOURCES = \
     src/impl/interop/interop_target.cpp \
     src/impl/transactions/transaction_impl.cpp \
     src/impl/transactions/transactions_impl.cpp \
+    src/impl/cluster/cluster_group_impl.cpp \
     src/impl/ignite_impl.cpp \
     src/transactions/transaction.cpp \
     src/transactions/transactions.cpp

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/Makefile.am
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/Makefile.am b/modules/platforms/cpp/core/include/Makefile.am
index fb84bc5..650f230 100644
--- a/modules/platforms/cpp/core/include/Makefile.am
+++ b/modules/platforms/cpp/core/include/Makefile.am
@@ -27,12 +27,16 @@ nobase_include_HEADERS = \
     ignite/impl/cache/query/query_fields_row_impl.h \
     ignite/impl/cache/query/query_impl.h \
     ignite/impl/cache/cache_impl.h \
+    ignite/impl/cache/cache_entry_processor_holder.h \
     ignite/impl/cache/query/query_batch.h \
     ignite/impl/interop/interop_target.h \
     ignite/impl/interop/interop_external_memory.h \
     ignite/impl/handle_registry.h \
     ignite/impl/transactions/transaction_impl.h \
     ignite/impl/transactions/transactions_impl.h \
+    ignite/impl/cluster/cluster_group_impl.h \
+    ignite/impl/ignite_binding_impl.h \
+    ignite/impl/module_manager.h \
     ignite/cache/query/query_fields_row.h \
     ignite/cache/query/query_fields_cursor.h \
     ignite/cache/query/query_scan.h \
@@ -45,7 +49,11 @@ nobase_include_HEADERS = \
     ignite/cache/cache.h \
     ignite/cache/cache_entry.h \
     ignite/cache/cache_peek_mode.h \
+    ignite/cache/cache_entry_processor.h \
+    ignite/cache/mutable_cache_entry.h \
     ignite/ignition.h \
+    ignite/ignite_binding.h \
+    ignite/ignite_binding_context.h \
     ignite/transactions/transaction.h \
     ignite/transactions/transaction_consts.h \
     ignite/transactions/transactions.h \

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/cache/cache.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/cache/cache.h b/modules/platforms/cpp/core/include/ignite/cache/cache.h
index 54c0f96..36a0470 100644
--- a/modules/platforms/cpp/core/include/ignite/cache/cache.h
+++ b/modules/platforms/cpp/core/include/ignite/cache/cache.h
@@ -40,7 +40,10 @@
 #include "ignite/cache/query/continuous/continuous_query_handle.h"
 #include "ignite/cache/query/continuous/continuous_query.h"
 #include "ignite/impl/cache/cache_impl.h"
+#include "ignite/impl/cache/cache_entry_processor_holder.h"
 #include "ignite/impl/operations.h"
+#include "ignite/impl/module_manager.h"
+#include "ignite/ignite_error.h"
 
 namespace ignite
 {
@@ -150,9 +153,9 @@ namespace ignite
              */
             bool ContainsKey(const K& key, IgniteError& err)
             {
-                impl::In1Operation<K> op(&key);
+                impl::In1Operation<K> op(key);
 
-                return impl.Get()->ContainsKey(op, &err);
+                return impl.Get()->ContainsKey(op, err);
             }
 
             /**
@@ -185,9 +188,9 @@ namespace ignite
              */
             bool ContainsKeys(const std::set<K>& keys, IgniteError& err)
             {
-                impl::InSetOperation<K> op(&keys);
+                impl::InSetOperation<K> op(keys);
 
-                return impl.Get()->ContainsKeys(op, &err);
+                return impl.Get()->ContainsKeys(op, err);
             }
 
             /**
@@ -230,10 +233,10 @@ namespace ignite
              */
             V LocalPeek(const K& key, int32_t peekModes, IgniteError& err)
             {
-                impl::InCacheLocalPeekOperation<K> inOp(&key, peekModes);
+                impl::InCacheLocalPeekOperation<K> inOp(key, peekModes);
                 impl::Out1Operation<V> outOp;
 
-                impl.Get()->LocalPeek(inOp, outOp, peekModes, &err);
+                impl.Get()->LocalPeek(inOp, outOp, peekModes, err);
 
                 return outOp.GetResult();
             }
@@ -276,10 +279,10 @@ namespace ignite
              */
             V Get(const K& key, IgniteError& err)
             {
-                impl::In1Operation<K> inOp(&key);
+                impl::In1Operation<K> inOp(key);
                 impl::Out1Operation<V> outOp;
 
-                impl.Get()->Get(inOp, outOp, &err);
+                impl.Get()->Get(inOp, outOp, err);
 
                 return outOp.GetResult();
             }
@@ -322,10 +325,10 @@ namespace ignite
              */
             std::map<K, V> GetAll(const std::set<K>& keys, IgniteError& err)
             {
-                impl::InSetOperation<K> inOp(&keys);
+                impl::InSetOperation<K> inOp(keys);
                 impl::OutMapOperation<K, V> outOp;
 
-                impl.Get()->GetAll(inOp, outOp, &err);
+                impl.Get()->GetAll(inOp, outOp, err);
 
                 return outOp.GetResult();
             }
@@ -362,9 +365,9 @@ namespace ignite
              */
             void Put(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> op(&key, &val);
+                impl::In2Operation<K, V> op(key, val);
 
-                impl.Get()->Put(op, &err);
+                impl.Get()->Put(op, err);
             }
 
             /**
@@ -397,9 +400,9 @@ namespace ignite
              */
             void PutAll(const std::map<K, V>& vals, IgniteError& err)
             {
-                impl::InMapOperation<K, V> op(&vals);
+                impl::InMapOperation<K, V> op(vals);
 
-                impl.Get()->PutAll(op, &err);
+                impl.Get()->PutAll(op, err);
             }
 
             /**
@@ -438,10 +441,10 @@ namespace ignite
              */
             V GetAndPut(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> inOp(&key, &val);
+                impl::In2Operation<K, V> inOp(key, val);
                 impl::Out1Operation<V> outOp;
 
-                impl.Get()->GetAndPut(inOp, outOp, &err);
+                impl.Get()->GetAndPut(inOp, outOp, err);
 
                 return outOp.GetResult();
             }
@@ -482,10 +485,10 @@ namespace ignite
              */
             V GetAndReplace(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> inOp(&key, &val);
+                impl::In2Operation<K, V> inOp(key, val);
                 impl::Out1Operation<V> outOp;
 
-                impl.Get()->GetAndReplace(inOp, outOp, &err);
+                impl.Get()->GetAndReplace(inOp, outOp, err);
 
                 return outOp.GetResult();
             }
@@ -520,10 +523,10 @@ namespace ignite
              */
             V GetAndRemove(const K& key, IgniteError& err)
             {
-                impl::In1Operation<K> inOp(&key);
+                impl::In1Operation<K> inOp(key);
                 impl::Out1Operation<V> outOp;
 
-                impl.Get()->GetAndRemove(inOp, outOp, &err);
+                impl.Get()->GetAndRemove(inOp, outOp, err);
 
                 return outOp.GetResult();
             }
@@ -562,9 +565,9 @@ namespace ignite
              */
             bool PutIfAbsent(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> op(&key, &val);
+                impl::In2Operation<K, V> op(key, val);
 
-                return impl.Get()->PutIfAbsent(op, &err);
+                return impl.Get()->PutIfAbsent(op, err);
             }
 
             /**
@@ -617,10 +620,10 @@ namespace ignite
              */
             V GetAndPutIfAbsent(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> inOp(&key, &val);
+                impl::In2Operation<K, V> inOp(key, val);
                 impl::Out1Operation<V> outOp;
 
-                impl.Get()->GetAndPutIfAbsent(inOp, outOp, &err);
+                impl.Get()->GetAndPutIfAbsent(inOp, outOp, err);
 
                 return outOp.GetResult();
             }
@@ -669,9 +672,9 @@ namespace ignite
              */
             bool Replace(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> op(&key, &val);
+                impl::In2Operation<K, V> op(key, val);
 
-                return impl.Get()->Replace(op, &err);
+                return impl.Get()->Replace(op, err);
             }
 
             /**
@@ -712,9 +715,9 @@ namespace ignite
              */
             bool Replace(const K& key, const V& oldVal, const V& newVal, IgniteError& err)
             {
-                impl::In3Operation<K, V, V> op(&key, &oldVal, &newVal);
+                impl::In3Operation<K, V, V> op(key, oldVal, newVal);
 
-                return impl.Get()->ReplaceIfEqual(op, &err);
+                return impl.Get()->ReplaceIfEqual(op, err);
             }
 
             /**
@@ -749,9 +752,9 @@ namespace ignite
              */
             void LocalEvict(const std::set<K>& keys, IgniteError& err)
             {
-                impl::InSetOperation<K> op(&keys);
+                impl::InSetOperation<K> op(keys);
 
-                impl.Get()->LocalEvict(op, &err);
+                impl.Get()->LocalEvict(op, err);
             }
 
             /**
@@ -777,7 +780,7 @@ namespace ignite
              */
             void Clear(IgniteError& err)
             {
-                impl.Get()->Clear(&err);
+                impl.Get()->Clear(err);
             }
 
             /**
@@ -808,9 +811,9 @@ namespace ignite
              */
             void Clear(const K& key, IgniteError& err)
             {
-                impl::In1Operation<K> op(&key);
+                impl::In1Operation<K> op(key);
 
-                impl.Get()->Clear(op, &err);
+                impl.Get()->Clear(op, err);
             }
 
             /**
@@ -841,9 +844,9 @@ namespace ignite
              */
             void ClearAll(const std::set<K>& keys, IgniteError& err)
             {
-                impl::InSetOperation<K> op(&keys);
+                impl::InSetOperation<K> op(keys);
 
-                impl.Get()->ClearAll(op, &err);
+                impl.Get()->ClearAll(op, err);
             }
 
             /**
@@ -880,9 +883,9 @@ namespace ignite
              */
             void LocalClear(const K& key, IgniteError& err)
             {
-                impl::In1Operation<K> op(&key);
+                impl::In1Operation<K> op(key);
 
-                impl.Get()->LocalClear(op, &err);
+                impl.Get()->LocalClear(op, err);
             }
 
             /**
@@ -919,9 +922,9 @@ namespace ignite
              */
             void LocalClearAll(const std::set<K>& keys, IgniteError& err)
             {
-                impl::InSetOperation<K> op(&keys);
+                impl::InSetOperation<K> op(keys);
 
-                impl.Get()->LocalClearAll(op, &err);
+                impl.Get()->LocalClearAll(op, err);
             }
 
             /**
@@ -968,9 +971,9 @@ namespace ignite
              */
             bool Remove(const K& key, IgniteError& err)
             {
-                impl::In1Operation<K> op(&key);
+                impl::In1Operation<K> op(key);
 
-                return impl.Get()->Remove(op, &err);
+                return impl.Get()->Remove(op, err);
             }
 
             /**
@@ -1009,9 +1012,9 @@ namespace ignite
              */
             bool Remove(const K& key, const V& val, IgniteError& err)
             {
-                impl::In2Operation<K, V> op(&key, &val);
+                impl::In2Operation<K, V> op(key, val);
 
-                return impl.Get()->RemoveIfEqual(op, &err);
+                return impl.Get()->RemoveIfEqual(op, err);
             }
 
             /**
@@ -1044,9 +1047,9 @@ namespace ignite
              */
             void RemoveAll(const std::set<K>& keys, IgniteError& err)
             {
-                impl::InSetOperation<K> op(&keys);
+                impl::InSetOperation<K> op(keys);
 
-                impl.Get()->RemoveAll(op, &err);
+                impl.Get()->RemoveAll(op, err);
             }
 
             /**
@@ -1077,7 +1080,7 @@ namespace ignite
              */
             void RemoveAll(IgniteError& err)
             {
-                return impl.Get()->RemoveAll(&err);
+                return impl.Get()->RemoveAll(err);
             }
 
             /**
@@ -1135,7 +1138,7 @@ namespace ignite
              */
             int32_t LocalSize(int32_t peekModes, IgniteError& err)
             {
-                return impl.Get()->Size(peekModes, true, &err);
+                return impl.Get()->Size(peekModes, true, err);
             }
 
             /**
@@ -1197,7 +1200,7 @@ namespace ignite
              */
             int32_t Size(int32_t peekModes, IgniteError& err)
             {
-                return impl.Get()->Size(peekModes, false, &err);
+                return impl.Get()->Size(peekModes, false, err);
             }
 
             /**
@@ -1230,7 +1233,7 @@ namespace ignite
              */
             query::QueryCursor<K, V> Query(const query::SqlQuery& qry, IgniteError& err)
             {
-                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QuerySql(qry, &err);
+                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QuerySql(qry, err);
 
                 return query::QueryCursor<K, V>(cursorImpl);
             }
@@ -1265,7 +1268,7 @@ namespace ignite
              */
             query::QueryCursor<K, V> Query(const query::TextQuery& qry, IgniteError& err)
             {
-                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QueryText(qry, &err);
+                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QueryText(qry, err);
 
                 return query::QueryCursor<K, V>(cursorImpl);
             }
@@ -1300,7 +1303,7 @@ namespace ignite
              */
             query::QueryCursor<K, V> Query(const query::ScanQuery& qry, IgniteError& err)
             {
-                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QueryScan(qry, &err);
+                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QueryScan(qry, err);
 
                 return query::QueryCursor<K, V>(cursorImpl);
             }
@@ -1335,12 +1338,122 @@ namespace ignite
              */
             query::QueryFieldsCursor Query(const query::SqlFieldsQuery& qry, IgniteError& err)
             {
-                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QuerySqlFields(qry, &err);
+                impl::cache::query::QueryCursorImpl* cursorImpl = impl.Get()->QuerySqlFields(qry, err);
 
                 return query::QueryFieldsCursor(cursorImpl);
             }
 
             /**
+             * Invokes an CacheEntryProcessor against the MutableCacheEntry
+             * specified by the provided key. If an entry does not exist for the
+             * specified key, an attempt is made to load it (if a loader is
+             * configured) or a surrogate entry, consisting of the key with a
+             * null value is used instead.
+             *
+             * Return value, processor and argument classes should all be
+             * default-constructable, copy-constructable and assignable. Also,
+             * BinaryType class template should be specialized for every custom
+             * class.
+             *
+             * Processor class should be registered as a cache entry processor using
+             * IgniteBinding::RegisterCacheEntryProcessor() method. You can declare
+             * #IgniteModuleInit() function to register your cache processors upon
+             * module loading. There should be at most one instance of such function
+             * per module.
+             *
+             * See the example below for details:
+             * @code{.cpp}
+             * IGNITE_EXPORTED_CALL void IgniteModuleInit(ignite::IgniteBindingContext& context)
+             * {
+             *     IgniteBinding binding = context.GetBingding();
+             *
+             *     binding.RegisterCacheEntryProcessor<MyProcessor1>();
+             *     binding.RegisterCacheEntryProcessor<MyProcessor2>();
+             *     // ...
+             *     binding.RegisterCacheEntryProcessor<MyProcessorN>();
+             * }
+             * @endcode
+             *
+             * Additionally, processor class should be derived from the
+             * ignite::CacheEntryProcessor class.
+             *
+             * @throw IgniteError on fail.
+             *
+             * @param key The key.
+             * @param processor The processor.
+             * @param arg The argument.
+             * @return Result of the processing.
+             */
+            template<typename R, typename P, typename A>
+            R Invoke(const K& key, const P& processor, const A& arg)
+            {
+                IgniteError err;
+
+                R res = Invoke<R>(key, processor, arg, err);
+
+                IgniteError::ThrowIfNeeded(err);
+
+                return res;
+            }
+
+            /**
+             * Invokes an CacheEntryProcessor against the MutableCacheEntry
+             * specified by the provided key. If an entry does not exist for the
+             * specified key, an attempt is made to load it (if a loader is
+             * configured) or a surrogate entry, consisting of the key with a
+             * null value is used instead.
+             *
+             * Return value, processor and argument classes should all be
+             * default-constructable, copy-constructable and assignable. Also,
+             * BinaryType class template should be specialized for every custom
+             * class.
+             *
+             * Processor class should be registered as a cache entry processor using
+             * IgniteBinding::RegisterCacheEntryProcessor() method. You can declare
+             * #IgniteModuleInit() function to register your cache processors upon
+             * module loading. There should be at most one instance of such function
+             * per module.
+             *
+             * See the example below for details:
+             * @code{.cpp}
+             * IGNITE_EXPORTED_CALL void IgniteModuleInit(ignite::IgniteBindingContext& context)
+             * {
+             *     IgniteBinding binding = context.GetBingding();
+             *
+             *     binding.RegisterCacheEntryProcessor<MyProcessor1>();
+             *     binding.RegisterCacheEntryProcessor<MyProcessor2>();
+             *     // ...
+             *     binding.RegisterCacheEntryProcessor<MyProcessorN>();
+             * }
+             * @endcode
+             *
+             * Additionally, processor class should be derived from the
+             * ignite::CacheEntryProcessor class.
+             *
+             * Sets err param which should be checked for the operation result.
+             *
+             * @param key The key.
+             * @param processor The processor.
+             * @param arg The argument.
+             * @param err Error.
+             * @return Result of the processing. Default-constructed value on error.
+             */
+            template<typename R, typename P, typename A>
+            R Invoke(const K& key, const P& processor, const A& arg, IgniteError& err)
+            {
+                typedef impl::cache::CacheEntryProcessorHolder<P, A> ProcessorHolder;
+
+                ProcessorHolder procHolder(processor, arg);
+
+                impl::In2Operation<K, ProcessorHolder> inOp(key, procHolder);
+                impl::Out1Operation<R> outOp;
+
+                impl.Get()->Invoke(inOp, outOp, err);
+
+                return outOp.GetResult();
+            }
+
+            /**
              * Start continuous query execution.
              *
              * @param qry Continuous query.

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/cache/cache_entry_processor.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/cache/cache_entry_processor.h b/modules/platforms/cpp/core/include/ignite/cache/cache_entry_processor.h
new file mode 100644
index 0000000..7fa1550
--- /dev/null
+++ b/modules/platforms/cpp/core/include/ignite/cache/cache_entry_processor.h
@@ -0,0 +1,111 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * @file
+ * Declares ignite::cache::CacheEntryProcessor class.
+ */
+
+#ifndef _IGNITE_CACHE_CACHE_ENTRY_PROCESSOR
+#define _IGNITE_CACHE_CACHE_ENTRY_PROCESSOR
+
+#include <ignite/common/common.h>
+#include <ignite/impl/binary/binary_reader_impl.h>
+#include <ignite/impl/binary/binary_writer_impl.h>
+#include <ignite/impl/cache/cache_entry_processor_holder.h>
+
+namespace ignite
+{
+    class IgniteBinding;
+
+    namespace cache
+    {
+        /**
+         * %Cache entry processor class template.
+         *
+         * Any cache processor should inherit from this class.
+         *
+         * All templated types should be default-constructable,
+         * copy-constructable and assignable.
+         *
+         * @tparam P The processor itself which inherits from CacheEntryProcessor.
+         * @tparam K Key type.
+         * @tparam V Value type.
+         * @tparam R Process method return type.
+         * @tparam A Process method argument type.
+         */
+        template<typename P, typename K, typename V, typename R, typename A>
+        class CacheEntryProcessor
+        {
+            friend class ignite::IgniteBinding;
+
+        public:
+            /**
+             * Destructor.
+             */
+            virtual ~CacheEntryProcessor()
+            {
+                // No-op.
+            }
+
+            /**
+             * Process entry, using input argument and return result.
+             *
+             * @param entry Entry to process.
+             * @param arg Argument.
+             * @return Processing result.
+             */
+            virtual R Process(MutableCacheEntry<K, V>& entry, const A& arg) = 0;
+
+        private:
+            /**
+             * Process input streaming data to produce output streaming data.
+             *
+             * Deserializes cache entry and processor using provided reader, invokes
+             * cache entry processor, gets result and serializes it using provided
+             * writer.
+             *
+             * @param reader Reader.
+             * @param writer Writer.
+             */
+            static void InternalProcess(impl::binary::BinaryReaderImpl& reader, impl::binary::BinaryWriterImpl& writer)
+            {
+                typedef impl::cache::CacheEntryProcessorHolder<P, A> ProcessorHolder;
+
+                ProcessorHolder procHolder = reader.ReadObject<ProcessorHolder>();
+
+                K key = reader.ReadObject<K>();
+
+                V value;
+                bool exists = reader.TryReadObject<V>(value);
+
+                impl::cache::MutableCacheEntryState entryState;
+
+                R res = procHolder.template Process<R, K, V>(key, value, exists, entryState);
+
+                writer.WriteInt8(static_cast<int8_t>(entryState));
+
+                if (entryState == impl::cache::ENTRY_STATE_VALUE_SET)
+                    writer.WriteTopObject(value);
+
+                writer.WriteTopObject(res);
+            }
+        };
+    }
+}
+
+#endif //_IGNITE_CACHE_CACHE_ENTRY_PROCESSOR

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/cache/mutable_cache_entry.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/cache/mutable_cache_entry.h b/modules/platforms/cpp/core/include/ignite/cache/mutable_cache_entry.h
new file mode 100644
index 0000000..0481a5e
--- /dev/null
+++ b/modules/platforms/cpp/core/include/ignite/cache/mutable_cache_entry.h
@@ -0,0 +1,176 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _IGNITE_CACHE_MUTABLE_CACHE_ENTRY
+#define _IGNITE_CACHE_MUTABLE_CACHE_ENTRY
+
+#include <ignite/common/common.h>
+#include <ignite/cache/cache_entry.h>
+
+namespace ignite
+{
+    namespace cache
+    {
+        /**
+         * Mutable representation of CacheEntry class template.
+         *
+         * Both key and value types should be default-constructable,
+         * copy-constructable and assignable.
+         *
+         * Additionally, equality operator should be defined for
+         * the value type.
+         */
+        template<typename K, typename V>
+        class MutableCacheEntry
+        {
+        public:
+            /**
+             * Default constructor.
+             */
+            MutableCacheEntry() :
+                key(),
+                val(),
+                exists(false)
+            {
+                // No-op.
+            }
+
+            /**
+             * Constructor for non-existing entry.
+             *
+             * @param key Key.
+             */
+            MutableCacheEntry(const K& key) :
+                key(key),
+                val(),
+                exists(false)
+            {
+                // No-op.
+            }
+
+            /**
+             * Constructor for existing entry.
+             *
+             * @param key Key.
+             * @param val Value.
+             */
+            MutableCacheEntry(const K& key, const V& val) :
+                key(key),
+                val(val),
+                exists(true)
+            {
+                // No-op.
+            }
+
+            /**
+             * Copy constructor.
+             *
+             * @param other Other instance.
+             */
+            MutableCacheEntry(const MutableCacheEntry& other) :
+                key(other.key),
+                val(other.val),
+                exists(other.exists)
+            {
+                // No-op.
+            }
+
+            /**
+             * Assignment operator.
+             *
+             * @param other Other instance.
+             * @return *this.
+             */
+            MutableCacheEntry& operator=(const MutableCacheEntry& other)
+            {
+                if (this != &other)
+                {
+                    key = other.key;
+                    val = other.val;
+                    exists = other.exists;
+                }
+
+                return *this;
+            }
+
+            /**
+             * Check whether cache entry exists in cache.
+             *
+             * @return True if the cache entry exists in cache and false
+             *     otherwise.
+             */
+            bool IsExists() const
+            {
+                return exists;
+            }
+
+            /**
+             * Removes the entry from the Cache.
+             */
+            void Remove()
+            {
+                exists = false;
+            }
+
+            /**
+             * Get key.
+             *
+             * @return Key.
+             */
+            const K& GetKey() const
+            {
+                return key;
+            }
+
+            /**
+             * Get value.
+             *
+             * @return Value.
+             */
+            const V& GetValue() const
+            {
+                return val;
+            }
+
+            /**
+             * Sets or replaces the value associated with the key.
+             *
+             * After setter invocation "IsExists" will return true.
+             *
+             * @param val Value to set.
+             */
+            void SetValue(const V& val)
+            {
+                this->val = val;
+
+                exists = true;
+            }
+
+        private:
+            /** Key. */
+            K key;
+
+            /** Value. */
+            V val;
+
+            /** Exists. */
+            bool exists;
+        };
+    }
+}
+
+#endif //_IGNITE_CACHE_MUTABLE_CACHE_ENTRY

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/cache/query/query_cursor.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/cache/query/query_cursor.h b/modules/platforms/cpp/core/include/ignite/cache/query/query_cursor.h
index 9057a03..61fd7ec 100644
--- a/modules/platforms/cpp/core/include/ignite/cache/query/query_cursor.h
+++ b/modules/platforms/cpp/core/include/ignite/cache/query/query_cursor.h
@@ -213,7 +213,7 @@ namespace ignite
                     impl::cache::query::QueryCursorImpl* impl0 = impl.Get();
 
                     if (impl0) {
-                        impl::OutQueryGetAllOperation<K, V> outOp(&res);
+                        impl::OutQueryGetAllOperation<K, V> outOp(res);
 
                         impl0->GetAll(outOp, err);
                     }

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/ignite.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/ignite.h b/modules/platforms/cpp/core/include/ignite/ignite.h
index 311dff2..140ee53 100644
--- a/modules/platforms/cpp/core/include/ignite/ignite.h
+++ b/modules/platforms/cpp/core/include/ignite/ignite.h
@@ -60,6 +60,15 @@ namespace ignite
         const char* GetName() const;
 
         /**
+         * Get node configuration.
+         *
+         * This method should only be used on the valid instance.
+         *
+         * @return Node configuration.
+         */
+        const IgniteConfiguration& GetConfiguration() const;
+
+        /**
          * Get cache.
          *
          * This method should only be used on the valid instance.
@@ -180,6 +189,15 @@ namespace ignite
         transactions::Transactions GetTransactions();
 
         /**
+         * Get ignite binding.
+         *
+         * This method should only be used on the valid instance.
+         *
+         * @return IgniteBinding class instance.
+         */
+        IgniteBinding GetBinding();
+
+        /**
          * Check if the instance is valid.
          *
          * Invalid instance can be returned if some of the previous

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/ignite_binding.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/ignite_binding.h b/modules/platforms/cpp/core/include/ignite/ignite_binding.h
new file mode 100644
index 0000000..a8decf9
--- /dev/null
+++ b/modules/platforms/cpp/core/include/ignite/ignite_binding.h
@@ -0,0 +1,119 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _IGNITE_IGNITE_BINDING
+#define _IGNITE_IGNITE_BINDING
+
+#include <ignite/common/common.h>
+#include <ignite/common/concurrent.h>
+
+#include <ignite/impl/ignite_binding_impl.h>
+
+namespace ignite
+{
+    /**
+     * %Ignite Binding.
+     * Used to register callable classes.
+     */
+    class IGNITE_IMPORT_EXPORT IgniteBinding
+    {
+    public:
+        /**
+         * Default constructor.
+         */
+        IgniteBinding() :
+            impl()
+        {
+            // No-op.
+        }
+
+        /**
+         * Constructor.
+         *
+         * @param impl Implementation.
+         */
+        IgniteBinding(common::concurrent::SharedPointer<impl::IgniteBindingImpl> impl) :
+            impl(impl)
+        {
+            // No-op.
+        }
+
+        /**
+         * Register Type as Cache Entry Processor.
+         *
+         * Registred type should be a child of ignite::cache::CacheEntryProcessor
+         * class.
+         *
+         * This method should only be used on the valid instance.
+         */
+        template<typename P>
+        void RegisterCacheEntryProcessor()
+        {
+            IgniteError err;
+
+            RegisterCacheEntryProcessor<P>(err);
+
+            IgniteError::ThrowIfNeeded(err);
+        }
+
+        /**
+         * Register Type as Cache Entry Processor.
+         *
+         * Registred type should be a child of ignite::cache::CacheEntryProcessor
+         * class.
+         *
+         * This method should only be used on the valid instance.
+         *
+         * @param err Error.
+         */
+        template<typename P>
+        void RegisterCacheEntryProcessor(IgniteError& err)
+        {
+            binary::BinaryType<P> bt;
+            impl::IgniteBindingImpl *im = impl.Get();
+
+            if (im)
+                im->RegisterCallback(bt.GetTypeId(), &P::CacheEntryProcessor::InternalProcess, err);
+            else
+            {
+                err = IgniteError(IgniteError::IGNITE_ERR_GENERIC,
+                    "Instance is not usable (did you check for error?).");
+            }
+        }
+
+        /**
+         * Check if the instance is valid.
+         *
+         * Invalid instance can be returned if some of the previous operations
+         * have resulted in a failure. For example invalid instance can be
+         * returned by not-throwing version of method in case of error. Invalid
+         * instances also often can be created using default constructor.
+         *
+         * @return True if the instance is valid and can be used.
+         */
+        bool IsValid() const
+        {
+            return impl.IsValid();
+        }
+
+    private:
+        /** Registered cache entry processors. */
+        common::concurrent::SharedPointer<impl::IgniteBindingImpl> impl;
+    };
+}
+
+#endif //_IGNITE_IGNITE_BINDING

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/ignite_binding_context.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/ignite_binding_context.h b/modules/platforms/cpp/core/include/ignite/ignite_binding_context.h
new file mode 100644
index 0000000..1a6d26d
--- /dev/null
+++ b/modules/platforms/cpp/core/include/ignite/ignite_binding_context.h
@@ -0,0 +1,88 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ * @file
+ * Declares ignite::IgniteBindingContext class.
+ */
+
+#ifndef _IGNITE_IGNITE_BINDING_CONTEXT
+#define _IGNITE_IGNITE_BINDING_CONTEXT
+
+#include <ignite/ignite_binding.h>
+#include <ignite/ignite_configuration.h>
+
+namespace ignite
+{
+    namespace impl
+    {
+        class IgniteEnvironment;
+    }
+
+    /**
+     * %Ignite binding context.
+     *
+     * Provides methods that can be used to get Ignite components which may be
+     * needed for initial module initialization.
+     */
+    class IgniteBindingContext
+    {
+        friend class impl::IgniteEnvironment;
+    public:
+        /**
+         * Get binding.
+         *
+         * @return IgniteBinding instance.
+         */
+        IgniteBinding GetBingding() const
+        {
+            return binding;
+        }
+
+        /**
+         * Get configuration for current node.
+         *
+         * @return Configuration.
+         */
+        const IgniteConfiguration& GetConfiguration() const
+        {
+            return cfg;
+        }
+
+    private:
+        /**
+         * Constructor.
+         *
+         * @param cfg Configuration.
+         * @param binding Binding.
+         */
+        IgniteBindingContext(const IgniteConfiguration& cfg, IgniteBinding binding) :
+            cfg(cfg),
+            binding(binding)
+        {
+            // No-op.
+        }
+
+        /** Configuration */
+        const IgniteConfiguration& cfg;
+
+        /** Binding. */
+        IgniteBinding binding;
+    };
+}
+
+#endif //_IGNITE_IGNITE_BINDING_CONTEXT
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/ignite_configuration.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/ignite_configuration.h b/modules/platforms/cpp/core/include/ignite/ignite_configuration.h
index 65c4550..885ffab 100644
--- a/modules/platforms/cpp/core/include/ignite/ignite_configuration.h
+++ b/modules/platforms/cpp/core/include/ignite/ignite_configuration.h
@@ -27,8 +27,6 @@
 #include <string>
 #include <list>
 
-#include <ignite/common/utils.h>
-
 namespace ignite
 {
     /**

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/impl/binary/binary_type_updater_impl.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/impl/binary/binary_type_updater_impl.h b/modules/platforms/cpp/core/include/ignite/impl/binary/binary_type_updater_impl.h
index bd21751..02ecd06 100644
--- a/modules/platforms/cpp/core/include/ignite/impl/binary/binary_type_updater_impl.h
+++ b/modules/platforms/cpp/core/include/ignite/impl/binary/binary_type_updater_impl.h
@@ -48,7 +48,7 @@ namespace ignite
                  */
                 ~BinaryTypeUpdaterImpl();
 
-                bool Update(Snap* snapshot, IgniteError* err);
+                bool Update(Snap* snapshot, IgniteError& err);
             private:
                 /** Environment. */
                 IgniteEnvironment& env;

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/impl/cache/cache_entry_processor_holder.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/impl/cache/cache_entry_processor_holder.h b/modules/platforms/cpp/core/include/ignite/impl/cache/cache_entry_processor_holder.h
new file mode 100644
index 0000000..23b57c3
--- /dev/null
+++ b/modules/platforms/cpp/core/include/ignite/impl/cache/cache_entry_processor_holder.h
@@ -0,0 +1,282 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _IGNITE_IMPL_CACHE_CACHE_ENTRY_PROCESSOR_HOLDER
+#define _IGNITE_IMPL_CACHE_CACHE_ENTRY_PROCESSOR_HOLDER
+
+#include <ignite/common/common.h>
+#include <ignite/cache/mutable_cache_entry.h>
+#include <ignite/binary/binary.h>
+
+namespace ignite
+{
+    namespace impl
+    {
+        namespace cache
+        {
+            /**
+             * Mutable Cache entry state.
+             */
+            enum MutableCacheEntryState
+            {
+                /** No changes have been committed to entry. */
+                ENTRY_STATE_INTACT = 0,
+
+                /** Value of the entry has been changed. */
+                ENTRY_STATE_VALUE_SET = 1,
+
+                /** Entry has been removed from cache. */
+                ENTRY_STATE_VALUE_REMOVED = 2,
+
+                /** Error occured. Represented in portable form. */
+                ENTRY_STATE_ERR_PORTABLE = 3,
+
+                /** Error occured. Represented in string form. */
+                ENTRY_STATE_ERR_STRING = 4
+            };
+
+            /**
+             * Get state of the mutable cache entry.
+             *
+             * @param valueBefore Cache entry value before mutation.
+             * @param existsBefore Flag for entry existence before mutation.
+             * @param valueBefore Cache entry value after mutation.
+             * @param existsBefore Flag for entry existence after mutation.
+             * @return Cache entry state.
+             */
+            template<typename V>
+            MutableCacheEntryState GetMutableCacheEntryState(const V& valueBefore, bool existsBefore,
+                                                             const V& valueAfter, bool existsAfter)
+            {
+                if ((!existsBefore && existsAfter) ||
+                    (existsBefore && existsAfter && !(valueBefore == valueAfter)))
+                    return ENTRY_STATE_VALUE_SET;
+
+                if (existsBefore && !existsAfter)
+                    return ENTRY_STATE_VALUE_REMOVED;
+
+                return ENTRY_STATE_INTACT;
+            }
+
+            /**
+             * Holder for the Cache Entry Processor and its argument. Used as a convenient way to
+             * transmit Cache Entry Processor between nodes.
+             *
+             * Both key and value types should be default-constructable,
+             * copy-constructable and assignable.
+             *
+             * Additionally, for the processor class public methods with the
+             * following signatures should be defined:
+             * @code{.cpp}
+             * // Should return unique ID for every class.
+             * static int64_t GetJobId();
+             *
+             * // Main processing method. Takes cache entry and argument and
+             * // returns processing result.
+             * R Process(ignite::cache::MutableCacheEntry<K, V>&, const A&);
+             * @endcode
+             */
+            template<typename P, typename A>
+            class CacheEntryProcessorHolder
+            {
+            public:
+                typedef P ProcessorType;
+                typedef A ArgumentType;
+
+                /**
+                 * Default constructor.
+                 */
+                CacheEntryProcessorHolder() :
+                    proc(),
+                    arg()
+                {
+                    // No-op.
+                }
+
+                /**
+                 * Constructor.
+                 *
+                 * @param proc Processor.
+                 * @param arg Argument.
+                 */
+                CacheEntryProcessorHolder(const P& proc, const A& arg) :
+                    proc(proc),
+                    arg(arg)
+                {
+                    // No-op.
+                }
+
+                /**
+                 * Destructor.
+                 */
+                ~CacheEntryProcessorHolder()
+                {
+                    // No-op.
+                }
+
+                /**
+                 * Get processor.
+                 *
+                 * @return Processor.
+                 */
+                const ProcessorType& getProcessor() const
+                {
+                    return proc;
+                }
+
+                /**
+                 * Get argument.
+                 *
+                 * @return Argument.
+                 */
+                const ArgumentType& getArgument() const
+                {
+                    return arg;
+                }
+
+                /**
+                 * Process key-value pair by the underlying Cache Entry Processor
+                 * using binded argument.
+                 *
+                 * Equality operator should be defined for the value type.
+                 *
+                 * @param key Cache entry key.
+                 * @param value Cache entry value. New value is stored here upon completion.
+                 * @param exists Entry existance indicator.
+                 * @param state State of the entry after the processing.
+                 * @return Result of the processing.
+                 */
+                template<typename R, typename K, typename V>
+                R Process(const K& key, V& value, bool exists, MutableCacheEntryState &state)
+                {
+                    typedef ignite::cache::MutableCacheEntry<K, V> Entry;
+
+                    Entry entry;
+
+                    if (exists)
+                        entry = Entry(key, value);
+                    else
+                        entry = Entry(key);
+
+                    R res = proc.Process(entry, arg);
+
+                    state = GetMutableCacheEntryState(value, exists, entry.GetValue(), entry.IsExists());
+
+                    value = entry.GetValue();
+
+                    return res;
+                }
+
+            private:
+                /** Stored processor. */
+                ProcessorType proc;
+
+                /** Stored argument. */
+                ArgumentType  arg;
+            };
+        }
+    }
+
+    namespace binary
+    {
+        /**
+         * Binary type specialization for CacheEntryProcessorHolder.
+         */
+        template<typename P, typename A>
+        struct BinaryType<impl::cache::CacheEntryProcessorHolder<P, A> >
+        {
+            typedef impl::cache::CacheEntryProcessorHolder<P, A> UnderlyingType;
+
+            IGNITE_BINARY_GET_FIELD_ID_AS_HASH
+            IGNITE_BINARY_GET_HASH_CODE_ZERO(UnderlyingType)
+            IGNITE_BINARY_IS_NULL_FALSE(UnderlyingType)
+            IGNITE_BINARY_GET_NULL_DEFAULT_CTOR(UnderlyingType)
+
+            int32_t GetTypeId()
+            {
+                static bool typeIdInited = false;
+                static int32_t typeId;
+                static common::concurrent::CriticalSection initLock;
+
+                if (typeIdInited)
+                    return typeId;
+
+                common::concurrent::CsLockGuard guard(initLock);
+
+                if (typeIdInited)
+                    return typeId;
+
+                typeId = GetBinaryStringHashCode(GetTypeName().c_str());
+                typeIdInited = true;
+
+                return typeId;
+            }
+
+            std::string GetTypeName()
+            {
+                // Using static variable and only initialize it once for better
+                // performance. Type name can't change in the course of the
+                // program flow.
+                static std::string name;
+                static common::concurrent::CriticalSection initLock;
+
+                // Name has been constructed already. Return it.
+                if (!name.empty())
+                    return name;
+
+                common::concurrent::CsLockGuard guard(initLock);
+
+                if (!name.empty())
+                    return name;
+
+                // Constructing name here.
+                BinaryType<P> p;
+
+                std::string procName = p.GetTypeName();
+
+                // -1 is for unnessecary null byte at the end of the C-string.
+                name.reserve(sizeof("CacheEntryProcessorHolder<>") - 1 + procName.size());
+
+                // Processor name is enough for identification as it is
+                // forbidden to register the same processor type several times.
+                name.append("CacheEntryProcessorHolder<").append(procName).push_back('>');
+
+                return name;
+            }
+
+            void Write(BinaryWriter& writer, UnderlyingType obj)
+            {
+                BinaryRawWriter raw = writer.RawWriter();
+
+                raw.WriteObject(obj.getProcessor());
+                raw.WriteObject(obj.getArgument());
+            }
+
+            UnderlyingType Read(BinaryReader& reader)
+            {
+                BinaryRawReader raw = reader.RawReader();
+
+                const P& proc = raw.ReadObject<P>();
+                const A& arg = raw.ReadObject<A>();
+
+                return UnderlyingType(proc, arg);
+            }
+        };
+    }
+}
+
+#endif //_IGNITE_IMPL_CACHE_CACHE_ENTRY_PROCESSOR_HOLDER

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/impl/cache/cache_impl.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/impl/cache/cache_impl.h b/modules/platforms/cpp/core/include/ignite/impl/cache/cache_impl.h
index 535e3ec..e6d49ef 100644
--- a/modules/platforms/cpp/core/include/ignite/impl/cache/cache_impl.h
+++ b/modules/platforms/cpp/core/include/ignite/impl/cache/cache_impl.h
@@ -69,7 +69,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result.
                  */
-                bool ContainsKey(InputOperation& inOp, IgniteError* err);
+                bool ContainsKey(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform ContainsKeys.
@@ -78,7 +78,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result.
                  */
-                bool ContainsKeys(InputOperation& inOp, IgniteError* err);
+                bool ContainsKeys(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform LocalPeek.
@@ -89,7 +89,7 @@ namespace ignite
                  * @param err Error.
                  */
                 void LocalPeek(InputOperation& inOp, OutputOperation& outOp, 
-                    int32_t peekModes, IgniteError* err);
+                    int32_t peekModes, IgniteError& err);
 
                 /**
                  * Perform Get.
@@ -98,7 +98,7 @@ namespace ignite
                  * @param outOp Output.
                  * @param err Error.
                  */
-                void Get(InputOperation& inOp, OutputOperation& outOp, IgniteError* err);
+                void Get(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
                 
                 /**
                  * Perform GetAll.
@@ -107,7 +107,7 @@ namespace ignite
                  * @param outOp Output.
                  * @param err Error.
                  */
-                void GetAll(InputOperation& inOp, OutputOperation& outOp, IgniteError* err);
+                void GetAll(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
 
                 /**
                  * Perform Put.
@@ -115,7 +115,7 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void Put(InputOperation& inOp, IgniteError* err);
+                void Put(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform PutAll.
@@ -123,7 +123,7 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void PutAll(InputOperation& inOp, IgniteError* err);
+                void PutAll(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform GetAndPut.
@@ -132,7 +132,7 @@ namespace ignite
                  * @param outOp Output.
                  * @param err Error.
                  */
-                void GetAndPut(InputOperation& inOp, OutputOperation& outOp, IgniteError* err);
+                void GetAndPut(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
 
                 /**
                  * Perform GetAndReplace.
@@ -141,7 +141,7 @@ namespace ignite
                  * @param outOp Output.
                  * @param err Error.
                  */
-                void GetAndReplace(InputOperation& inOp, OutputOperation& outOp, IgniteError* err);
+                void GetAndReplace(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
 
                 /**
                  * Perform GetAndRemove.
@@ -150,7 +150,7 @@ namespace ignite
                  * @param outOp Output.
                  * @param err Error.
                  */
-                void GetAndRemove(InputOperation& inOp, OutputOperation& outOp, IgniteError* err);
+                void GetAndRemove(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
 
                 /**
                  * Perform PutIfAbsent.
@@ -159,7 +159,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result
                  */
-                bool PutIfAbsent(InputOperation& inOp, IgniteError* err);
+                bool PutIfAbsent(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform GetAndPutIfAbsent.
@@ -168,7 +168,7 @@ namespace ignite
                  * @param outOp Output.
                  * @param err Error.
                  */
-                void GetAndPutIfAbsent(InputOperation& inOp, OutputOperation& outOp, IgniteError* err);
+                void GetAndPutIfAbsent(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
 
                 /**
                  * Perform Replace(K, V).
@@ -177,7 +177,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result
                  */
-                bool Replace(InputOperation& inOp, IgniteError* err);
+                bool Replace(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform Replace(K, V, V).
@@ -186,7 +186,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result
                  */
-                bool ReplaceIfEqual(InputOperation& inOp, IgniteError* err);
+                bool ReplaceIfEqual(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform LocalEvict.
@@ -194,14 +194,14 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void LocalEvict(InputOperation& inOp, IgniteError* err);
+                void LocalEvict(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform Clear.
                  *
                  * @param err Error.
                  */
-                void Clear(IgniteError* err);
+                void Clear(IgniteError& err);
 
                 /**
                  * Perform Clear.
@@ -209,7 +209,7 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void Clear(InputOperation& inOp, IgniteError* err);
+                void Clear(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform ClearAll.
@@ -217,7 +217,7 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void ClearAll(InputOperation& inOp, IgniteError* err);
+                void ClearAll(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform LocalClear.
@@ -225,7 +225,7 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void LocalClear(InputOperation& inOp, IgniteError* err);
+                void LocalClear(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform LocalClearAll.
@@ -233,7 +233,7 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void LocalClearAll(InputOperation& inOp, IgniteError* err);
+                void LocalClearAll(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform Remove(K).
@@ -242,7 +242,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result
                  */
-                bool Remove(InputOperation& inOp, IgniteError* err);
+                bool Remove(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform Remove(K, V).
@@ -251,7 +251,7 @@ namespace ignite
                  * @param err Error.
                  * @return Result
                  */
-                bool RemoveIfEqual(InputOperation& inOp, IgniteError* err);
+                bool RemoveIfEqual(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform RemoveAll.
@@ -259,14 +259,14 @@ namespace ignite
                  * @param inOp Input.
                  * @param err Error.
                  */
-                void RemoveAll(InputOperation& inOp, IgniteError* err);
+                void RemoveAll(InputOperation& inOp, IgniteError& err);
 
                 /**
                  * Perform RemoveAll.
                  *
                  * @param err Error.
                  */
-                void RemoveAll(IgniteError* err);
+                void RemoveAll(IgniteError& err);
 
                 /**
                 * Perform Size.
@@ -275,7 +275,7 @@ namespace ignite
                 * @param local Local flag.
                 * @param err Error.
                 */
-                int32_t Size(int32_t peekModes, bool local, IgniteError* err);
+                int32_t Size(int32_t peekModes, bool local, IgniteError& err);
 
                 /**
                  * Invoke query.
@@ -284,7 +284,7 @@ namespace ignite
                  * @param err Error.
                  * @return Query cursor.
                  */
-                query::QueryCursorImpl* QuerySql(const ignite::cache::query::SqlQuery& qry, IgniteError* err);
+                query::QueryCursorImpl* QuerySql(const ignite::cache::query::SqlQuery& qry, IgniteError& err);
 
                 /**
                  * Invoke text query.
@@ -293,7 +293,7 @@ namespace ignite
                  * @param err Error.
                  * @return Query cursor.
                  */
-                query::QueryCursorImpl* QueryText(const ignite::cache::query::TextQuery& qry, IgniteError* err);
+                query::QueryCursorImpl* QueryText(const ignite::cache::query::TextQuery& qry, IgniteError& err);
 
                 /**
                  * Invoke scan query.
@@ -302,7 +302,7 @@ namespace ignite
                  * @param err Error.
                  * @return Query cursor.
                  */
-                query::QueryCursorImpl* QueryScan(const ignite::cache::query::ScanQuery& qry, IgniteError* err);
+                query::QueryCursorImpl* QueryScan(const ignite::cache::query::ScanQuery& qry, IgniteError& err);
 
                 /**
                  * Invoke sql fields query.
@@ -311,7 +311,16 @@ namespace ignite
                  * @param err Error.
                  * @return Query cursor.
                  */
-                query::QueryCursorImpl* QuerySqlFields(const ignite::cache::query::SqlFieldsQuery& qry, IgniteError* err);
+                query::QueryCursorImpl* QuerySqlFields(const ignite::cache::query::SqlFieldsQuery& qry, IgniteError& err);
+
+                /**
+                 * Perform Invoke.
+                 *
+                 * @param inOp Input.
+                 * @param outOp Output.
+                 * @param err Error.
+                 */
+                void Invoke(InputOperation& inOp, OutputOperation& outOp, IgniteError& err);
 
                 /**
                  * Start continuous query execution.
@@ -374,7 +383,7 @@ namespace ignite
                  * @param err Error.
                  */
                 template<typename T>
-                query::QueryCursorImpl* QueryInternal(const T& qry, int32_t typ, IgniteError* err)
+                query::QueryCursorImpl* QueryInternal(const T& qry, int32_t typ, IgniteError& err)
                 {
                     ignite::jni::java::JniErrorInfo jniErr;
 
@@ -447,7 +456,7 @@ namespace ignite
                     jobject qryJavaRef = GetEnvironment().Context()->CacheOutOpContinuousQuery(GetTarget(),
                         cmd, mem.Get()->PointerLong(), &jniErr);
 
-                    IgniteError::SetError(jniErr.code, jniErr.errCls, jniErr.errMsg, &err);
+                    IgniteError::SetError(jniErr.code, jniErr.errCls, jniErr.errMsg, err);
 
                     if (jniErr.code == java::IGNITE_JNI_ERR_SUCCESS)
                         return new query::continuous::ContinuousQueryHandleImpl(GetEnvironmentPointer(), handle, qryJavaRef);

http://git-wip-us.apache.org/repos/asf/ignite/blob/1410900f/modules/platforms/cpp/core/include/ignite/impl/cluster/cluster_group_impl.h
----------------------------------------------------------------------
diff --git a/modules/platforms/cpp/core/include/ignite/impl/cluster/cluster_group_impl.h b/modules/platforms/cpp/core/include/ignite/impl/cluster/cluster_group_impl.h
new file mode 100644
index 0000000..2bff0d8
--- /dev/null
+++ b/modules/platforms/cpp/core/include/ignite/impl/cluster/cluster_group_impl.h
@@ -0,0 +1,77 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _IGNITE_IMPL_CLUSTER_CLUSTER_GROUP_IMPL
+#define _IGNITE_IMPL_CLUSTER_CLUSTER_GROUP_IMPL
+
+#include <ignite/common/concurrent.h>
+#include <ignite/jni/java.h>
+
+#include <ignite/impl/interop/interop_target.h>
+
+namespace ignite
+{
+    namespace impl
+    {
+        namespace cluster
+        {
+            /**
+             * Cluster group implementation.
+             */
+            class IGNITE_FRIEND_EXPORT ClusterGroupImpl : private interop::InteropTarget
+            {
+                typedef common::concurrent::SharedPointer<IgniteEnvironment> SP_IgniteEnvironment;
+                typedef common::concurrent::SharedPointer<ClusterGroupImpl> SP_ClusterGroupImpl;
+            public:
+                /**
+                 * Constructor used to create new instance.
+                 *
+                 * @param env Environment.
+                 * @param javaRef Reference to java object.
+                 */
+                ClusterGroupImpl(SP_IgniteEnvironment env, jobject javaRef);
+
+                /**
+                 * Destructor.
+                 */
+                ~ClusterGroupImpl();
+
+                /**
+                 * Get server nodes cluster group implementation.
+                 *
+                 * @param err Error.
+                 * @return Server nodes cluster group implementation.
+                 */
+                SP_ClusterGroupImpl ForServers(IgniteError& err);
+
+            private:
+                /**
+                 * Make cluster group implementation using java reference and
+                 * internal state of this cluster group.
+                 *
+                 * @param javaRef Java reference to cluster group to be created.
+                 * @return New cluster group implementation.
+                 */
+                SP_ClusterGroupImpl FromTarget(jobject javaRef);
+
+                IGNITE_NO_COPY_ASSIGNMENT(ClusterGroupImpl)
+            };
+        }
+    }
+}
+
+#endif //_IGNITE_IMPL_CLUSTER_CLUSTER_GROUP_IMPL
\ No newline at end of file