diff --git a/src/Classic/Utilities/MSLang.cpp b/src/Classic/Utilities/MSLang.cpp
index 640975792a8c6d06d2183d3a24cd25fa4f7a4da4..a8ff8a0a90c4877c40200ac39c23dbe1bdc4f0f0 100644
--- a/src/Classic/Utilities/MSLang.cpp
+++ b/src/Classic/Utilities/MSLang.cpp
@@ -1,8 +1,10 @@
 #include "Utilities/MSLang.h"
+#include "Utilities/PortableBitmapReader.h"
 #include "Algorithms/Quaternion.h"
 #include "Physics/Physics.h"
 
 #include <boost/regex.hpp>
+#include <boost/filesystem.hpp>
 
 #include <iostream>
 #include <string>
@@ -591,6 +593,62 @@ namespace mslang {
         }
     };
 
+    struct Mask: public Function {
+        static
+        bool parse_detail(iterator &it, const iterator &end, Function* &fun) {
+            Mask *pixmap = static_cast<Mask*>(fun);
+
+            std::string str(it, end);
+            std::cout << str << std::endl;
+            boost::regex argument("'([^\\0]+)'(\\).*)");
+            boost::smatch what;
+            if (!boost::regex_match(str, what, argument)) return false;
+
+            std::string filename = what[1];
+            std::cout << filename << std::endl;
+            if (!boost::filesystem::exists(filename)) {
+                ERRORMSG("file '" << filename << "' doesn't exists" << endl);
+                return false;
+            }
+
+            PortableBitmapReader reader(filename);
+            unsigned int width = reader.getWidth();
+            unsigned int height = reader.getHeight();
+            double pixel_width = 0.001;
+            double pixel_height = 0.001;
+
+            for (unsigned int i = 0; i < height; ++ i) {
+                for (unsigned int j = 0; j < width; ++ j) {
+                    if (reader.isBlack(i, j)) {
+                        Rectangle rect;
+                        rect.width_m = pixel_width;
+                        rect.height_m = pixel_height;
+                        rect.trafo_m = AffineTransformation(Vector_t(1, 0, (j - 0.5 * width) * pixel_width),
+                                                            Vector_t(0, 1, (0.5 * height - i) * pixel_height));
+                        // rect.computeBoundingBox();
+                        pixmap->pixels_m.push_back(rect);
+                        pixmap->pixels_m.back().computeBoundingBox();
+                    }
+                }
+            }
+
+            std::string fullMatch = what[0];
+            std::string rest = what[2];
+            it += (fullMatch.size() - rest.size() + 1);
+
+            return true;
+        }
+
+        virtual void print(int ident) {
+            for (auto pix: pixels_m) pix.print(ident);
+        }
+
+        virtual void apply(std::vector<Base*> &bfuncs) {
+            for (auto pix: pixels_m) pix.apply(bfuncs);
+        }
+
+        std::vector<Rectangle> pixels_m;
+    };
 
     QuadTree::QuadTree(const QuadTree &right):
         level_m(right.level_m),
@@ -794,6 +852,10 @@ namespace mslang {
             // it = it2;
 
             return true;
+        } else if (identifier == "mask") {
+            fun = new Mask;
+            it += shift;
+            return Mask::parse_detail(it, end, fun);
         }
 
 
diff --git a/tools/mslang/mslang.cpp b/tools/mslang/mslang.cpp
index 9b5ac71d1e40c9fb29420b0a4c506792ff075199..bf29090566c9202090a16dba315e636fbcfe9481 100644
--- a/tools/mslang/mslang.cpp
+++ b/tools/mslang/mslang.cpp
@@ -86,6 +86,7 @@ int main(int argc, char *argv[])
 
             mslang::QuadTree tree;
             tree.bb_m = mslang::BoundingBox(llc, urc);
+            std::cout << tree.bb_m << std::endl;
             tree.objects_m.insert(tree.objects_m.end(), baseBlocks.begin(), baseBlocks.end());
             tree.buildUp();
 
@@ -94,51 +95,52 @@ int main(int argc, char *argv[])
 
             out.close();
 
-            out.open("particles.gpl");
-            gsl_rng *rng = gsl_rng_alloc(gsl_rng_default);
+            if (false) {
+                out.open("particles.gpl");
+                gsl_rng *rng = gsl_rng_alloc(gsl_rng_default);
 
-            unsigned int n = 0;
-            IpplTimings::TimerRef mainTimer = IpplTimings::getTimer("mainTimer");
-            IpplTimings::startTimer(mainTimer);
+                unsigned int n = 0;
+                IpplTimings::TimerRef mainTimer = IpplTimings::getTimer("mainTimer");
+                IpplTimings::startTimer(mainTimer);
 
-            for (unsigned int i = 0; i < N; ++ i) {
-                Vector_t X(0.0);
-                X[0] = llc[0] + (urc[0] - llc[0]) * gsl_rng_uniform(rng);
-                X[1] = llc[1] + (urc[1] - llc[1]) * gsl_rng_uniform(rng);
+                for (unsigned int i = 0; i < N; ++ i) {
+                    Vector_t X(0.0);
+                    X[0] = llc[0] + (urc[0] - llc[0]) * gsl_rng_uniform(rng);
+                    X[1] = llc[1] + (urc[1] - llc[1]) * gsl_rng_uniform(rng);
 
 
-                if (method == 0) {
-                    if (tree.isInside(X)) {
-                        ++ n;
-                        out << std::setw(14) << X[0]
-                            << std::setw(14) << X[1]
-                            << std::endl;
-                    }
-                } else {
-                    for (mslang::Base* func: baseBlocks) {
-                        if (func->isInside(X)) {
+                    if (method == 0) {
+                        if (tree.isInside(X)) {
                             ++ n;
                             out << std::setw(14) << X[0]
                                 << std::setw(14) << X[1]
                                 << std::endl;
-                            break;
+                        }
+                    } else {
+                        for (mslang::Base* func: baseBlocks) {
+                            if (func->isInside(X)) {
+                                ++ n;
+                                out << std::setw(14) << X[0]
+                                    << std::setw(14) << X[1]
+                                    << std::endl;
+                                break;
+                            }
                         }
                     }
                 }
+                IpplTimings::stopTimer(mainTimer);
+
+                std::cout << (double)n / N * 100 << " % of particles passed" << std::endl;
+
+                std::map<std::string, unsigned int> characteristicValues;
+                characteristicValues.insert(std::make_pair("method", method));
+                characteristicValues.insert(std::make_pair("num particles", N));
+                characteristicValues.insert(std::make_pair("num base functions", baseBlocks.size()));
+                std::stringstream ss;
+                ss << "timing__m_=_" << method << "__np_=_" << N << "__nbf_=_" << baseBlocks.size() << ".dat";
+                IpplTimings::print(ss.str(), characteristicValues);
+                gsl_rng_free(rng);
             }
-            IpplTimings::stopTimer(mainTimer);
-
-            std::cout << (double)n / N * 100 << " % of particles passed" << std::endl;
-
-            std::map<std::string, unsigned int> characteristicValues;
-            characteristicValues.insert(std::make_pair("method", method));
-            characteristicValues.insert(std::make_pair("num particles", N));
-            characteristicValues.insert(std::make_pair("num base functions", baseBlocks.size()));
-            std::stringstream ss;
-            ss << "timing__m_=_" << method << "__np_=_" << N << "__nbf_=_" << baseBlocks.size() << ".dat";
-            IpplTimings::print(ss.str(), characteristicValues);
-            gsl_rng_free(rng);
-
 
             for (mslang::Base* func: baseBlocks) {
                 delete func;