[opengtl-commits] [371] add a tool to benchmark openctl

[ Thread Index | Date Index | More lists.tuxfamily.org/opengtl-commits Archives ]


Revision: 371
Author:   cyrille
Date:     2008-09-07 09:38:53 +0200 (Sun, 07 Sep 2008)

Log Message:
-----------
add a tool to benchmark openctl

Modified Paths:
--------------
    trunk/OpenGTL/OpenCTL/tools/CMakeLists.txt

Added Paths:
-----------
    trunk/OpenGTL/OpenCTL/tools/benchmark/
    trunk/OpenGTL/OpenCTL/tools/benchmark/CMakeLists.txt
    trunk/OpenGTL/OpenCTL/tools/benchmark/CtlBenchmark.cpp


Modified: trunk/OpenGTL/OpenCTL/tools/CMakeLists.txt
===================================================================
--- trunk/OpenGTL/OpenCTL/tools/CMakeLists.txt	2008-09-07 07:37:50 UTC (rev 370)
+++ trunk/OpenGTL/OpenCTL/tools/CMakeLists.txt	2008-09-07 07:38:53 UTC (rev 371)
@@ -1,2 +1,3 @@
 add_subdirectory(compiler)
 add_subdirectory(interpreter)
+add_subdirectory(benchmark)

Added: trunk/OpenGTL/OpenCTL/tools/benchmark/CMakeLists.txt
===================================================================
--- trunk/OpenGTL/OpenCTL/tools/benchmark/CMakeLists.txt	                        (rev 0)
+++ trunk/OpenGTL/OpenCTL/tools/benchmark/CMakeLists.txt	2008-09-07 07:38:53 UTC (rev 371)
@@ -0,0 +1,8 @@
+include_directories( ${CMAKE_SOURCE_DIR} )
+
+set(ctlbenchmark_SRCS
+  CtlBenchmark.cpp
+    )
+
+add_executable(ctlbenchmark ${ctlbenchmark_SRCS})
+target_link_libraries(ctlbenchmark OpenCTL )

Added: trunk/OpenGTL/OpenCTL/tools/benchmark/CtlBenchmark.cpp
===================================================================
--- trunk/OpenGTL/OpenCTL/tools/benchmark/CtlBenchmark.cpp	                        (rev 0)
+++ trunk/OpenGTL/OpenCTL/tools/benchmark/CtlBenchmark.cpp	2008-09-07 07:38:53 UTC (rev 371)
@@ -0,0 +1,326 @@
+/*
+ *  Copyright (c) 2007-2008 Cyrille Berger <cberger@xxxxxxxxxxx>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation;
+ * version 2 of the License.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this library; see the file COPYING.  If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+// C++ Headers
+#include <iostream>
+#include <fstream>
+#include <cstdlib>
+#include <sys/time.h>
+#include <vector>
+
+#include <GTLCore/Array.h>
+#include <GTLCore/PixelDescription.h>
+#include <GTLCore/Type.h>
+
+// OpenCTL Headers
+#include <OpenCTL/Module.h>
+#include <OpenCTL/ModulesManager.h>
+#include <OpenCTL/Program.h>
+#include <OpenCTL/Version.h>
+
+class PointF {
+  public:
+    PointF(double x, double y) : m_x(x), m_y(y)
+    {
+    }
+    double x() const { return m_x; }
+    double y() const { return m_y; }
+  private:
+    double m_x, m_y;
+};
+
+float interpolateCubic1D (const std::vector<PointF>& table, double p)
+{
+  if( p <= table[0].x() ) return table[0].y();
+  if( p >= table[table.size()-1].x() ) return table[table.size()-1].y();
+  
+  for( std::size_t i = 0; i < table.size() - 1; ++i )
+  {
+    if( table[i].x() <= p && p < table[i+1].x() )
+    {
+      double s = (p - table[i].x()) / (table[i+1].x() - table[i].x());
+      double dx1 = (table[i+1].x() - table[i].x());
+      double dy1 = (table[i+1].y() - table[i].y());
+      
+      double m0;
+      double m1;
+      if( i > 0 )
+      {
+        double dy0 = (table[i].y() - table[i-1].y());
+        double dx0 = (table[i].x() - table[i-1].x());
+        m0 = (dy1 + dx1 * dy0 / dx0) / 2;
+      }
+      if( i < table.size()-2 )
+      {
+        double dx2 = (table[i+2].x() - table[i+1].x());
+        double dy2 = (table[i+2].y() - table[i+1].y());
+        m1 = (dy1 + dx1 * dy2 / dx2) / 2;
+      }
+      if( i == 0) {
+        m0 = (3 * dy1 - m1) / 2;
+      }
+      if( i == table.size()-2 )
+      {
+        m1 = (3 * dy1 - m0) / 2;
+      }
+      return table[i].y() * (2 * s*s*s - 3 * s*s + 1) +
+          m0 * (s*s*s - 2 * s*s + s) +
+          table[i+1].y() * (-2 * s*s*s + 3 * s*s) +
+          m1 * (s*s*s - s*s);
+    }
+  }
+  return 0.0;
+}
+
+void printVersion()
+{
+  std::cout << OpenCTL::LibraryShortName << " - " << OpenCTL::LibraryName << " - " << OpenCTL::LibraryVersionString << std::endl;
+  std::cout << OpenCTL::LibraryCopyright << std::endl;
+  std::cout << "CTL Version : " << OpenCTL::LanguageVersion << std::endl;
+}
+void printHelp()
+{
+  std::cout << "Usage : ctlbenchmark" << std::endl;
+  std::cout << std::endl;
+  std::cout << "  -h --help               print this message" << std::endl;
+  std::cout << "  -v --version            print the version information" << std::endl;
+}
+
+#define ARG_IS(a,b) argv[ai] == GTLCore::String(a) or argv[ai] == GTLCore::String(b)
+
+class Benchmark {
+  public:
+    Benchmark(int runCount, GTLCore::Array* array ) : m_array(array), m_runCount(runCount)  {}
+    void start()
+    {
+      initialise();
+      m_totalTime = 0;
+      m_bestTime = 0x0FFFFFFF;
+      m_worseTime = 0;
+      timeval timeBefore, timeAfter;
+      for(int i = 0; i < m_runCount; ++i)
+      {
+        gettimeofday( &timeBefore, 0 );
+        run();
+        gettimeofday( &timeAfter, 0 );
+        int delta = timeAfter.tv_usec - timeBefore.tv_usec + 1000000 * (timeAfter.tv_sec - timeBefore.tv_sec);
+        if(delta > m_worseTime) m_worseTime = delta;
+        if(delta < m_bestTime) m_bestTime = delta;
+        m_totalTime += delta;
+      }
+      return;
+    }
+    int totalTime()
+    {
+      return m_totalTime;
+    }
+    int bestTime()
+    {
+      return m_bestTime;
+    }
+    int worseTime()
+    {
+      return m_worseTime;
+    }
+    int meanTime()
+    {
+      return m_totalTime / m_runCount;
+    }
+    void dump()
+    {
+      std::cout << "Total: " << totalTime() << " mean: " << meanTime() << " best: " << bestTime() << " worse: " << worseTime() << std::endl;
+    }
+  protected:
+    virtual void initialise() = 0;
+    virtual void run() = 0;
+    GTLCore::Array* array() { return m_array; }
+  private:
+    GTLCore::Array* m_array;
+    int m_runCount;
+    int m_totalTime;
+    int m_bestTime;
+    int m_worseTime;
+};
+
+class CtlBenchmark : public Benchmark {
+  protected:
+    CtlBenchmark(const std::vector< PointF >& _points, int runCount, GTLCore::Array* array ) : Benchmark(runCount, array ), points(_points), program(0) {}
+    GTLCore::String sourceCode() const;
+    void compile();
+    void apply();
+  private:
+     GTLCore::String valueListToCTL( const std::vector<PointF>& _points, double _scale ) const;
+     std::vector< PointF > points;
+     OpenCTL::Program* program;
+};
+
+void CtlBenchmark::compile()
+{
+    OpenCTL::Module p("");
+    p.setSource( sourceCode() );
+    p.compile();
+    if(not p.isCompiled())
+    {
+      std::cout << "Error: " << std::endl << p.compilationErrorsMessage() << std::endl;
+      abort();
+    }
+    program = new OpenCTL::Program( "apply", &p, GTLCore::PixelDescription( GTLCore::Type::Float, 4) );
+}
+
+void CtlBenchmark::apply()
+{
+  program->apply( *array(), *array() );
+}
+
+GTLCore::String CtlBenchmark::valueListToCTL( const std::vector<PointF>& _points, double _scale ) const
+{
+  GTLCore::String result = "{ {";
+  for(std::size_t i = 0; i < _points.size(); ++i)
+  {
+    PointF point = _points[i];
+    result += GTLCore::String::number(point.x() * _scale) + "," + GTLCore::String::number(point.y() * _scale) + "}";
+    if( i != _points.size() - 1)
+    {
+      result += ",{";
+    }
+  }
+  return result + " }";
+}
+
+GTLCore::String CtlBenchmark::sourceCode() const
+{
+  GTLCore::String program16Src = "const float lightTable[][2] = " + valueListToCTL( points, 1.0 ) + ";";
+  program16Src += "void apply( float rIn, float gIn, float bIn, float aIn, output float rOut, output float gOut, output float bOut, output float aOut) \
+  { \
+      rOut = interpolateCubic1D( lightTable, rIn); \
+      gOut = interpolateCubic1D( lightTable, gIn); \
+      bOut = interpolateCubic1D( lightTable, bIn); \
+      aOut = aIn; \
+  }";
+  return program16Src;
+}
+
+class CompileEachTimeCtlBenchmark : public CtlBenchmark {
+  public:
+    CompileEachTimeCtlBenchmark(const std::vector< PointF >& points, int runCount, GTLCore::Array* array ) : CtlBenchmark(points, runCount, array ) {}
+  protected:
+    virtual void initialise()
+    {
+    }
+    virtual void run()
+    {
+      compile();
+      apply();
+    }
+};
+
+class CompileOnceCtlBenchmark : public CtlBenchmark {
+  public:
+    CompileOnceCtlBenchmark(const std::vector< PointF >& points, int runCount, GTLCore::Array* array ) : CtlBenchmark(points, runCount, array ) {}
+  protected:
+    virtual void initialise()
+    {
+      compile();
+    }
+    virtual void run()
+    {
+      apply();
+    }
+};
+
+int main(int argc, char** argv)
+{
+  GTLCore::String fileName = "";
+  for(int ai = 1; ai < argc; ai++)
+  {
+    if(ARG_IS("-h","--help"))
+    {
+      printHelp();
+      return EXIT_SUCCESS;
+    } else if(ARG_IS("-v","--version"))
+    {
+      printVersion();
+      return EXIT_SUCCESS;
+    } else {
+      if( ai != argc - 1)
+      {
+        std::cerr << "Invalid command line parameters." << std::endl;
+      } else {
+        fileName = argv[ai];
+      }
+    }
+  }
+  std::vector< PointF > points;
+  points.push_back( PointF( 0.0, 0.0) );
+  points.push_back( PointF( 0.3, 0.2) );
+  points.push_back( PointF( 0.5, 0.5) );
+  points.push_back( PointF( 0.6, 0.8) );
+  points.push_back( PointF( 1.0, 1.0) );
+  
+  GTLCore::PixelDescription pd( GTLCore::Type::Float, 4);
+  GTLCore::Array array( 1000000 * pd.bitsSize() / 8 );
+  
+  {
+    std::cout << "Compile once " << std::endl;
+    CompileOnceCtlBenchmark benchmark(points, 100, &array);
+    benchmark.start();
+    benchmark.dump();
+  }
+  
+  {
+    std::cout << "Compile each time " << std::endl;
+    CompileEachTimeCtlBenchmark benchmark(points, 100, &array);
+    benchmark.start();
+    benchmark.dump();
+  }
+  
+/*  if( fileName == "")
+  {
+    printHelp();
+  } else {
+    GTLCore::String source;
+    std::ifstream in;
+    in.open(fileName.c_str() );
+    if(not in)
+    {
+      std::cerr << "Impossible to open file " << fileName << std::endl;
+      return EXIT_FAILURE;
+    }
+    GTLCore::String str;
+    std::getline(in,str);
+    while ( in ) {
+      source += str;
+      source += "\n";
+      std::getline(in,str);
+    }
+    OpenCTL::Module p(fileName);
+    p.setSource( source );
+    p.compile();
+    if(not p.isCompiled())
+    {
+      std::cout << "Error: " << std::endl << p.compilationErrorsMessage() << std::endl;
+      return EXIT_FAILURE;
+    }
+    if( showAssembly )
+    {
+      std::cout << p.asmSourceCode();
+    }
+  }*/
+  return EXIT_SUCCESS;
+}


Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/