[Mesa-dev] [PATCH] clover: Cache serialized binaries

Tom Stellard tom at stellard.net
Mon Jun 16 07:47:48 PDT 2014


On Sun, Jun 15, 2014 at 01:08:14PM +0200, Francisco Jerez wrote:
> Tom Stellard <thomas.stellard at amd.com> writes:
> 
> > We were serializing the binaries once when clGetProgramInfo was called
> > with CL_PROGRAM_BINARY_SIZES and then again when it was called with
> > CL_PROGRAM_BINARIES.  This was slowing down some OpenCV tests which were
> > building binary kernel caches.
> >
> > This improves the run-time of OpenCV's OCL_ImgProc/CvtColor8u.*
> > test from 7 minutes to 1 minute.
> > ---
> 
> Can you give the attached two patches a try?  I'm curious to see if they
> have a comparable effect -- If they do I'd prefer to fix the underlying
> object rather than caching binaries in serialized form.
> 
> Thanks.
> 
> >[...]
> 

These patches improve performance even more.  Now it only takes 10 seconds to
run the tests instead of 7 minutes.

For both patches:

Tested-by: Tom Stellard <thomas.stellard at amd.com>

> From a500126213b073793184b0b6f170a58229340778 Mon Sep 17 00:00:00 2001
> From: Francisco Jerez <currojerez at riseup.net>
> Date: Sat, 14 Jun 2014 20:53:35 +0200
> Subject: [PATCH 1/2] clover: Optimize module serialization for vectors of
>  fundamental types.
> 
> ---
>  src/gallium/state_trackers/clover/core/module.cpp | 23 ++++++++++++++++++++++-
>  1 file changed, 22 insertions(+), 1 deletion(-)
> 
> diff --git a/src/gallium/state_trackers/clover/core/module.cpp b/src/gallium/state_trackers/clover/core/module.cpp
> index 3e3ad99..41de734 100644
> --- a/src/gallium/state_trackers/clover/core/module.cpp
> +++ b/src/gallium/state_trackers/clover/core/module.cpp
> @@ -69,7 +69,9 @@ namespace {
>  
>     /// (De)serialize a vector.
>     template<typename T>
> -   struct _serializer<compat::vector<T>> {
> +   struct _serializer<compat::vector<T>,
> +                      typename std::enable_if<
> +                         !std::is_scalar<T>::value>::type> {
>        static void
>        proc(compat::ostream &os, const compat::vector<T> &v) {
>           _proc<uint32_t>(os, v.size());
> @@ -87,6 +89,25 @@ namespace {
>        }
>     };
>  
> +   template<typename T>
> +   struct _serializer<compat::vector<T>,
> +                      typename std::enable_if<
> +                         std::is_scalar<T>::value>::type> {
> +      static void
> +      proc(compat::ostream &os, const compat::vector<T> &v) {
> +         _proc<uint32_t>(os, v.size());
> +         os.write(reinterpret_cast<const char *>(v.begin()),
> +                  v.size() * sizeof(T));
> +      }
> +
> +      static void
> +      proc(compat::istream &is, compat::vector<T> &v) {
> +         v.reserve(_proc<uint32_t>(is));
> +         is.read(reinterpret_cast<char *>(v.begin()),
> +                 v.size() * sizeof(T));
> +      }
> +   };
> +
>     /// (De)serialize a module::section.
>     template<>
>     struct _serializer<module::section> {
> -- 
> 1.9.2
> 

> From 1267038c2b0621dddc3d5c7718eed7ef2beb111b Mon Sep 17 00:00:00 2001
> From: Francisco Jerez <currojerez at riseup.net>
> Date: Sat, 14 Jun 2014 21:03:02 +0200
> Subject: [PATCH 2/2] clover: Calculate the serialized size of a module
>  efficiently.
> 
> ---
>  src/gallium/state_trackers/clover/api/program.cpp |  5 +---
>  src/gallium/state_trackers/clover/core/module.cpp | 32 +++++++++++++++++++++++
>  src/gallium/state_trackers/clover/core/module.hpp |  1 +
>  3 files changed, 34 insertions(+), 4 deletions(-)
> 
> diff --git a/src/gallium/state_trackers/clover/api/program.cpp b/src/gallium/state_trackers/clover/api/program.cpp
> index fedc91d..a14baa3 100644
> --- a/src/gallium/state_trackers/clover/api/program.cpp
> +++ b/src/gallium/state_trackers/clover/api/program.cpp
> @@ -190,10 +190,7 @@ clGetProgramInfo(cl_program d_prog, cl_program_info param,
>  
>     case CL_PROGRAM_BINARY_SIZES:
>        buf.as_vector<size_t>() = map([&](const device &dev) {
> -            compat::ostream::buffer_t bin;
> -            compat::ostream s(bin);
> -            prog.binary(dev).serialize(s);
> -            return bin.size();
> +            return prog.binary(dev).size();
>           },
>           prog.devices());
>        break;
> diff --git a/src/gallium/state_trackers/clover/core/module.cpp b/src/gallium/state_trackers/clover/core/module.cpp
> index 41de734..55ed91a 100644
> --- a/src/gallium/state_trackers/clover/core/module.cpp
> +++ b/src/gallium/state_trackers/clover/core/module.cpp
> @@ -52,6 +52,13 @@ namespace {
>        return x;
>     }
>  
> +   /// Calculate the size of the specified object.
> +   template<typename T>
> +   void
> +   _proc(module::size_t &sz, const T &x) {
> +      _serializer<T>::proc(sz, x);
> +   }
> +
>     /// (De)serialize a scalar value.
>     template<typename T>
>     struct _serializer<T, typename std::enable_if<
> @@ -65,6 +72,11 @@ namespace {
>        proc(compat::istream &is, T &x) {
>           is.read(reinterpret_cast<char *>(&x), sizeof(x));
>        }
> +
> +      static void
> +      proc(module::size_t &sz, const T &x) {
> +         sz += sizeof(x);
> +      }
>     };
>  
>     /// (De)serialize a vector.
> @@ -87,6 +99,14 @@ namespace {
>           for (size_t i = 0; i < v.size(); i++)
>              new(&v[i]) T(_proc<T>(is));
>        }
> +
> +      static void
> +      proc(module::size_t &sz, const compat::vector<T> &v) {
> +         sz += sizeof(uint32_t);
> +
> +         for (size_t i = 0; i < v.size(); i++)
> +            _proc<T>(sz, v[i]);
> +      }
>     };
>  
>     template<typename T>
> @@ -106,6 +126,11 @@ namespace {
>           is.read(reinterpret_cast<char *>(v.begin()),
>                   v.size() * sizeof(T));
>        }
> +
> +      static void
> +      proc(module::size_t &sz, const compat::vector<T> &v) {
> +         sz += sizeof(uint32_t) + sizeof(T) * v.size();
> +      }
>     };
>  
>     /// (De)serialize a module::section.
> @@ -170,4 +195,11 @@ namespace clover {
>     module::deserialize(compat::istream &is) {
>        return _proc<module>(is);
>     }
> +
> +   module::size_t
> +   module::size() const {
> +      size_t sz = 0;
> +      _proc(sz, *this);
> +      return sz;
> +   }
>  }
> diff --git a/src/gallium/state_trackers/clover/core/module.hpp b/src/gallium/state_trackers/clover/core/module.hpp
> index 4a8dbcb..18a5bfb 100644
> --- a/src/gallium/state_trackers/clover/core/module.hpp
> +++ b/src/gallium/state_trackers/clover/core/module.hpp
> @@ -105,6 +105,7 @@ namespace clover {
>  
>        void serialize(compat::ostream &os) const;
>        static module deserialize(compat::istream &is);
> +      size_t size() const;
>  
>        compat::vector<symbol> syms;
>        compat::vector<section> secs;
> -- 
> 1.9.2
> 




> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/mesa-dev



More information about the mesa-dev mailing list