Pārlūkot izejas kodu

improved constant propagation

Nicolas Winkler 5 gadi atpakaļ
vecāks
revīzija
5847b788a2

+ 0 - 27
libmandel/include/IterationCompiler.h

@@ -20,33 +20,6 @@ namespace mnd
 }
 void squareTest();
 
-class mnd::CompiledGenerator : public mnd::MandelGenerator
-{
-    std::unique_ptr<ExecData> execData;
-public:
-    CompiledGenerator(MandelContext& mndContext);
-    CompiledGenerator(std::unique_ptr<ExecData> execData);
-    CompiledGenerator(CompiledGenerator&&);
-    virtual ~CompiledGenerator(void);
-    virtual void generate(const MandelInfo& info, float* data);
-
-    std::string dump(void) const;
-};
-
-
-#ifdef WITH_OPENCL
-class mnd::CompiledClGenerator : public mnd::ClGeneratorFloat
-{
-public:
-    CompiledClGenerator(const MandelDevice& device, const std::string& code);
-    //virtual ~CompiledGenerator(void);
-    //virtual void generate(const MandelInfo& info, float* data);
-    virtual std::string getKernelCode(bool smooth) const override;
-    virtual void generate(const MandelInfo& info, float* data);
-
-    //std::string dump(void) const;
-};
-#endif // WITH_OPENCL
 
 
 namespace mnd

+ 37 - 0
libmandel/include/IterationGenerator.h

@@ -2,6 +2,7 @@
 #define MANDEL_ITERATIONGENERATOR_H
 
 #include "Generators.h"
+#include "ClGenerators.h"
 #include "IterationFormula.h"
 
 #include <utility>
@@ -12,6 +13,12 @@ namespace mnd
     class IterationGenerator;
 
     class NaiveGenerator;
+    class CompiledGenerator;
+    class CompiledClGenerator;
+
+    // forward declaration
+    struct ExecData;
+    class MandelDevice;
 }
 
 
@@ -35,5 +42,35 @@ private:
     std::complex<double> calc(mnd::Expression& expr, std::complex<double> z, std::complex<double> c);
 };
 
+
+class mnd::CompiledGenerator : public mnd::MandelGenerator
+{
+    std::unique_ptr<ExecData> execData;
+public:
+    CompiledGenerator(std::unique_ptr<ExecData> execData);
+    CompiledGenerator(CompiledGenerator&&);
+    virtual ~CompiledGenerator(void);
+    virtual void generate(const MandelInfo& info, float* data);
+
+    std::string dump(void) const;
+};
+
+
+#ifdef WITH_OPENCL
+class mnd::CompiledClGenerator : public mnd::ClGeneratorFloat
+{
+public:
+    CompiledClGenerator(const MandelDevice& device, const std::string& code);
+    //virtual ~CompiledGenerator(void);
+    //virtual void generate(const MandelInfo& info, float* data);
+    virtual std::string getKernelCode(bool smooth) const override;
+    virtual void generate(const MandelInfo& info, float* data);
+
+    //std::string dump(void) const;
+};
+#endif // WITH_OPENCL
+
+
+
 #endif // MANDEL_ITERATIONGENERATOR_H
 

+ 1 - 143
libmandel/src/IterationCompiler.cpp

@@ -1,10 +1,10 @@
 #include "IterationCompiler.h"
 
+#include "ExecData.h"
 #include "Mandel.h"
 #include "OpenClInternal.h"
 #include "OpenClCode.h"
 
-#include <asmjit/asmjit.h>
 #include <cmath>
 #include <omp.h>
 #include <any>
@@ -13,31 +13,6 @@
 using namespace std::string_literals;
 namespace mnd
 {
-    struct ExecData
-    {
-        std::unique_ptr<asmjit::JitRuntime> jitRuntime;
-        std::unique_ptr<asmjit::CodeHolder> code;
-        std::unique_ptr<asmjit::x86::Compiler> compiler;
-        void* iterationFunc;
-
-        ExecData(void) :
-            jitRuntime{ std::make_unique<asmjit::JitRuntime>() },
-            code{ std::make_unique<asmjit::CodeHolder>() },
-            compiler{ nullptr },
-            iterationFunc{ nullptr }
-        {
-            code->init(jitRuntime->codeInfo());
-            compiler = std::make_unique<asmjit::x86::Compiler>(code.get());
-        }
-
-        ExecData(ExecData&&) = default;
-        ExecData(const ExecData&) = delete;
-        ExecData& operator=(ExecData&&) = default;
-        ExecData& operator=(const ExecData&) = delete;
-
-        ~ExecData(void) = default;
-    };
-
 
     struct CompileVisitor
     {
@@ -413,123 +388,6 @@ namespace mnd
 #endif
 }
 
-
-using mnd::CompiledGenerator;
-using mnd::CompiledClGenerator;
-
-
-
-CompiledGenerator::CompiledGenerator(mnd::MandelContext& mndContext) :
-    MandelGenerator{ 1.0e-15 },
-    execData{ std::make_unique<ExecData>(compile(mndContext)) }
-{
-}
-
-
-CompiledGenerator::CompiledGenerator(std::unique_ptr<mnd::ExecData> execData) :
-    MandelGenerator{ 1.0e-15 },
-    execData{ std::move(execData) }
-{
-}
-
-
-CompiledGenerator::CompiledGenerator(CompiledGenerator&&) = default;
-
-
-CompiledGenerator::~CompiledGenerator(void)
-{
-}
-
-    
-/*__declspec(noinline)
-int iter(double x, double y, int maxIter)
-{
-    int k = 0;
-
-    double a = x;
-    double b = y;
-
-    for (k = 0; k < maxIter; k++) {
-        double aa = a * a;
-        double bb = b * b;
-        double abab = a * b + a * b;
-        a = aa - bb + x;
-        b = abab + y;
-        if (aa + bb >= 16)
-            break;
-    }
-
-    return k;
-}*/
-
-
-
-void CompiledGenerator::generate(const mnd::MandelInfo& info, float* data)
-{
-    using IterFunc = int (*)(double, double, int);
-
-    omp_set_num_threads(omp_get_num_procs());
-#pragma omp parallel for schedule(static, 1)
-    for (int i = 0; i < info.bHeight; i++) {
-        double y = mnd::convert<double>(info.view.y + info.view.height * i / info.bHeight);
-        for (int j = 0; j < info.bWidth; j++) {
-            double x = mnd::convert<double>(info.view.x + info.view.width * j / info.bWidth);
-            IterFunc iterFunc = asmjit::ptr_as_func<IterFunc>(this->execData->iterationFunc);
-            int k = iterFunc(x, y, info.maxIter);
-            data[i * info.bWidth + j] = k;
-        }
-    }
-}
-
-
-std::string CompiledGenerator::dump(void) const
-{
-    asmjit::String d;
-    execData->compiler->dump(d);
-    return d.data();
-}
-
-
-#ifdef WITH_OPENCL
-CompiledClGenerator::CompiledClGenerator(const mnd::MandelDevice& device, const std::string& code) :
-    ClGeneratorFloat{ device.getClDevice().device, code }
-{
-}
-
-
-std::string CompiledClGenerator::getKernelCode(bool smooth) const
-{
-    return "";
-}
-
-void CompiledClGenerator::generate(const mnd::MandelInfo& info, float* data)
-{
-    ::size_t bufferSize = info.bWidth * info.bHeight * sizeof(float);
-
-    cl::Buffer buffer_A(context, CL_MEM_WRITE_ONLY, bufferSize);
-    float pixelScaleX = float(info.view.width / info.bWidth);
-    float pixelScaleY = float(info.view.height / info.bHeight);
-
-    static cl::Kernel iterate = cl::Kernel(program, "iterate");
-    iterate.setArg(0, buffer_A);
-    iterate.setArg(1, int(info.bWidth));
-    iterate.setArg(2, float(info.view.x));
-    iterate.setArg(3, float(info.view.y));
-    iterate.setArg(4, float(pixelScaleX));
-    iterate.setArg(5, float(pixelScaleY));
-    iterate.setArg(6, int(info.maxIter));
-    iterate.setArg(7, int(info.smooth ? 1 : 0));
-    iterate.setArg(8, int(info.julia ? 1 : 0));
-    iterate.setArg(9, float(info.juliaX));
-    iterate.setArg(10, float(info.juliaY));
-
-    queue.enqueueNDRangeKernel(iterate, 0, cl::NDRange(info.bWidth * info.bHeight));
-
-    queue.enqueueReadBuffer(buffer_A, CL_TRUE, 0, bufferSize, data);
-}
-
-#endif // WITH_OPENCL
-
 using namespace asmjit;
 
 struct Visitor

+ 115 - 1
libmandel/src/IterationGenerator.cpp

@@ -1,4 +1,9 @@
 #include "IterationGenerator.h"
+#include "ExecData.h"
+#include "Mandel.h"
+
+#include "OpenClInternal.h"
+
 
 #include <omp.h>
 
@@ -15,7 +20,6 @@ IterationGenerator::IterationGenerator(IterationFormula itf,
 }
 
 
-
 NaiveGenerator::NaiveGenerator(IterationFormula itf,
                                    const mnd::Real& prec) :
     IterationGenerator{ std::move(itf), prec }
@@ -124,3 +128,113 @@ std::complex<double> NaiveGenerator::calc(mnd::Expression& expr, std::complex<do
 }
 
 
+
+using mnd::CompiledGenerator;
+using mnd::CompiledClGenerator;
+
+
+CompiledGenerator::CompiledGenerator(std::unique_ptr<mnd::ExecData> execData) :
+    MandelGenerator{ 1.0e-15 },
+    execData{ std::move(execData) }
+{
+}
+
+
+CompiledGenerator::CompiledGenerator(CompiledGenerator&&) = default;
+
+
+CompiledGenerator::~CompiledGenerator(void)
+{
+}
+
+
+/*__declspec(noinline)
+int iter(double x, double y, int maxIter)
+{
+int k = 0;
+
+double a = x;
+double b = y;
+
+for (k = 0; k < maxIter; k++) {
+double aa = a * a;
+double bb = b * b;
+double abab = a * b + a * b;
+a = aa - bb + x;
+b = abab + y;
+if (aa + bb >= 16)
+break;
+}
+
+return k;
+}*/
+
+
+
+void CompiledGenerator::generate(const mnd::MandelInfo& info, float* data)
+{
+    using IterFunc = int (*)(double, double, int);
+
+    omp_set_num_threads(omp_get_num_procs());
+#pragma omp parallel for schedule(static, 1)
+    for (int i = 0; i < info.bHeight; i++) {
+        double y = mnd::convert<double>(info.view.y + info.view.height * i / info.bHeight);
+        for (int j = 0; j < info.bWidth; j++) {
+            double x = mnd::convert<double>(info.view.x + info.view.width * j / info.bWidth);
+            IterFunc iterFunc = asmjit::ptr_as_func<IterFunc>(this->execData->iterationFunc);
+            int k = iterFunc(x, y, info.maxIter);
+            data[i * info.bWidth + j] = k;
+        }
+    }
+}
+
+
+std::string CompiledGenerator::dump(void) const
+{
+    asmjit::String d;
+    execData->compiler->dump(d);
+    return d.data();
+}
+
+
+#ifdef WITH_OPENCL
+CompiledClGenerator::CompiledClGenerator(const mnd::MandelDevice& device, const std::string& code) :
+    ClGeneratorFloat{ device.getClDevice().device, code }
+{
+}
+
+
+std::string CompiledClGenerator::getKernelCode(bool smooth) const
+{
+    return "";
+}
+
+void CompiledClGenerator::generate(const mnd::MandelInfo& info, float* data)
+{
+    ::size_t bufferSize = info.bWidth * info.bHeight * sizeof(float);
+
+    cl::Buffer buffer_A(context, CL_MEM_WRITE_ONLY, bufferSize);
+    float pixelScaleX = float(info.view.width / info.bWidth);
+    float pixelScaleY = float(info.view.height / info.bHeight);
+
+    static cl::Kernel iterate = cl::Kernel(program, "iterate");
+    iterate.setArg(0, buffer_A);
+    iterate.setArg(1, int(info.bWidth));
+    iterate.setArg(2, float(info.view.x));
+    iterate.setArg(3, float(info.view.y));
+    iterate.setArg(4, float(pixelScaleX));
+    iterate.setArg(5, float(pixelScaleY));
+    iterate.setArg(6, int(info.maxIter));
+    iterate.setArg(7, int(info.smooth ? 1 : 0));
+    iterate.setArg(8, int(info.julia ? 1 : 0));
+    iterate.setArg(9, float(info.juliaX));
+    iterate.setArg(10, float(info.juliaY));
+
+    queue.enqueueNDRangeKernel(iterate, 0, cl::NDRange(info.bWidth * info.bHeight));
+
+    queue.enqueueReadBuffer(buffer_A, CL_TRUE, 0, bufferSize, data);
+}
+
+#endif // WITH_OPENCL
+
+