[Beignet] [PATCH 2/3] GBE/Runtime: pass the device id to the compiler backend.

Chuanbo Weng chuanbo.weng at intel.com
Thu Apr 17 00:06:09 PDT 2014


From: Zhigang Gong <zhigang.gong at linux.intel.com>

For some reason, we need to know current target device id
at the code generation stage. This patch introduces such
a mechanism. This is the preparation for the baytrail werid
hang issue fixing.

Signed-off-by: Zhigang Gong <zhigang.gong at linux.intel.com>
---
 backend/src/backend/gen_context.cpp |  5 +++--
 backend/src/backend/gen_context.hpp |  4 +++-
 backend/src/backend/gen_encoder.cpp |  4 ++--
 backend/src/backend/gen_encoder.hpp |  5 ++++-
 backend/src/backend/gen_program.cpp | 14 ++++++++------
 backend/src/backend/gen_program.hpp |  4 +++-
 backend/src/backend/program.cpp     |  5 +++--
 backend/src/backend/program.h       |  8 +++++---
 backend/src/gbe_bin_generater.cpp   |  4 +++-
 src/cl_program.c                    |  6 +++---
 10 files changed, 37 insertions(+), 22 deletions(-)

diff --git a/backend/src/backend/gen_context.cpp b/backend/src/backend/gen_context.cpp
index 50f10c5..6b18c84 100644
--- a/backend/src/backend/gen_context.cpp
+++ b/backend/src/backend/gen_context.cpp
@@ -44,11 +44,12 @@ namespace gbe
   ///////////////////////////////////////////////////////////////////////////
   GenContext::GenContext(const ir::Unit &unit,
                          const std::string &name,
+                         uint32_t deviceID,
                          bool limitRegisterPressure,
                          bool relaxMath) :
-    Context(unit, name), limitRegisterPressure(limitRegisterPressure), relaxMath(relaxMath)
+    Context(unit, name), deviceID(deviceID), limitRegisterPressure(limitRegisterPressure), relaxMath(relaxMath)
   {
-    this->p = GBE_NEW(GenEncoder, simdWidth, 7); // XXX handle more than Gen7
+    this->p = GBE_NEW(GenEncoder, simdWidth, 7, deviceID); // XXX handle more than Gen7
     this->sel = GBE_NEW(Selection, *this);
     this->ra = GBE_NEW(GenRegAllocator, *this);
   }
diff --git a/backend/src/backend/gen_context.hpp b/backend/src/backend/gen_context.hpp
index d24d05b..1154796 100644
--- a/backend/src/backend/gen_context.hpp
+++ b/backend/src/backend/gen_context.hpp
@@ -52,9 +52,11 @@ namespace gbe
     /*! Create a new context. name is the name of the function we want to
      *  compile
      */
-    GenContext(const ir::Unit &unit, const std::string &name, bool limitRegisterPressure = false, bool relaxMath = false);
+    GenContext(const ir::Unit &unit, const std::string &name, uint32_t deviceID, bool limitRegisterPressure = false, bool relaxMath = false);
     /*! Release everything needed */
     ~GenContext(void);
+    /*! Target device ID*/
+    uint32_t deviceID;
     /*! Implements base class */
     virtual bool emitCode(void);
     /*! Function we emit code for */
diff --git a/backend/src/backend/gen_encoder.cpp b/backend/src/backend/gen_encoder.cpp
index 9df031e..c991661 100644
--- a/backend/src/backend/gen_encoder.cpp
+++ b/backend/src/backend/gen_encoder.cpp
@@ -216,8 +216,8 @@ namespace gbe
   //////////////////////////////////////////////////////////////////////////
   // Gen Emitter encoding class
   //////////////////////////////////////////////////////////////////////////
-  GenEncoder::GenEncoder(uint32_t simdWidth, uint32_t gen) :
-    stateNum(0), gen(gen)
+  GenEncoder::GenEncoder(uint32_t simdWidth, uint32_t gen, uint32_t deviceID) :
+    stateNum(0), gen(gen), deviceID(deviceID)
   {
     this->curr.execWidth = simdWidth;
     this->curr.quarterControl = GEN_COMPRESSION_Q1;
diff --git a/backend/src/backend/gen_encoder.hpp b/backend/src/backend/gen_encoder.hpp
index 50662fb..1c30ec7 100644
--- a/backend/src/backend/gen_encoder.hpp
+++ b/backend/src/backend/gen_encoder.hpp
@@ -56,6 +56,7 @@
 #include "sys/platform.hpp"
 #include "sys/vector.hpp"
 #include <cassert>
+#include "src/cl_device_data.h"
 
 namespace gbe
 {
@@ -64,7 +65,7 @@ namespace gbe
   {
   public:
     /*! simdWidth is the default width for the instructions */
-    GenEncoder(uint32_t simdWidth, uint32_t gen);
+    GenEncoder(uint32_t simdWidth, uint32_t gen, uint32_t deviceID);
     /*! Size of the stack (should be large enough) */
     enum { MAX_STATE_NUM = 16 };
     /*! Push the current instruction state */
@@ -81,6 +82,8 @@ namespace gbe
     uint32_t stateNum;
     /*! Gen generation to encode */
     uint32_t gen;
+    /*! Device ID */
+    uint32_t deviceID;
 
     ////////////////////////////////////////////////////////////////////////
     // Encoding functions
diff --git a/backend/src/backend/gen_program.cpp b/backend/src/backend/gen_program.cpp
index 1f157e0..240ae4f 100644
--- a/backend/src/backend/gen_program.cpp
+++ b/backend/src/backend/gen_program.cpp
@@ -71,7 +71,6 @@ namespace gbe {
     fclose(f);
   }
 
-  GenProgram::GenProgram(void) {}
   GenProgram::~GenProgram(void) {}
 
   /*! We must avoid spilling at all cost with Gen */
@@ -102,7 +101,7 @@ namespace gbe {
 
       // Force the SIMD width now and try to compile
       unit.getFunction(name)->setSimdWidth(simdWidth);
-      Context *ctx = GBE_NEW(GenContext, unit, name, limitRegisterPressure, relaxMath);
+      Context *ctx = GBE_NEW(GenContext, unit, name, deviceID, limitRegisterPressure, relaxMath);
       kernel = ctx->compileKernel();
       if (kernel != NULL) {
         break;
@@ -116,12 +115,14 @@ namespace gbe {
     return kernel;
   }
 
-  static gbe_program genProgramNewFromBinary(const char *binary, size_t size) {
+  static gbe_program genProgramNewFromBinary(uint32_t deviceID, const char *binary, size_t size) {
     using namespace gbe;
     std::string binary_content;
     binary_content.assign(binary, size);
-    GenProgram *program = GBE_NEW_NO_ARG(GenProgram);
+    GenProgram *program = GBE_NEW(GenProgram, deviceID);
     std::istringstream ifs(binary_content, std::ostringstream::binary);
+    // FIXME we need to check the whether the current device ID match the binary file's.
+    deviceID = deviceID;
 
     if (!program->deserializeFromBin(ifs)) {
       delete program;
@@ -148,14 +149,15 @@ namespace gbe {
     return sz;
   }
 
-  static gbe_program genProgramNewFromLLVM(const char *fileName,
+  static gbe_program genProgramNewFromLLVM(uint32_t deviceID,
+                                           const char *fileName,
                                            size_t stringSize,
                                            char *err,
                                            size_t *errSize,
                                            int optLevel)
   {
     using namespace gbe;
-    GenProgram *program = GBE_NEW_NO_ARG(GenProgram);
+    GenProgram *program = GBE_NEW(GenProgram, deviceID);
     std::string error;
     // Try to compile the program
     if (program->buildFromLLVMFile(fileName, error, optLevel) == false) {
diff --git a/backend/src/backend/gen_program.hpp b/backend/src/backend/gen_program.hpp
index 189c262..ea54b49 100644
--- a/backend/src/backend/gen_program.hpp
+++ b/backend/src/backend/gen_program.hpp
@@ -58,7 +58,9 @@ namespace gbe
   {
   public:
     /*! Create an empty program */
-    GenProgram(void);
+    GenProgram(uint32_t deviceID) : deviceID(deviceID) {}
+    /*! Current device ID*/
+    uint32_t deviceID;
     /*! Destroy the program */
     virtual ~GenProgram(void);
     /*! Implements base class */
diff --git a/backend/src/backend/program.cpp b/backend/src/backend/program.cpp
index 91abbae..79622e0 100644
--- a/backend/src/backend/program.cpp
+++ b/backend/src/backend/program.cpp
@@ -690,7 +690,8 @@ namespace gbe {
   extern std::string ocl_stdlib_str;
 
   BVAR(OCL_USE_PCH, true);
-  static gbe_program programNewFromSource(const char *source,
+  static gbe_program programNewFromSource(uint32_t deviceID,
+                                          const char *source,
                                           size_t stringSize,
                                           const char *options,
                                           char *err,
@@ -829,7 +830,7 @@ namespace gbe {
         err += *errSize;
         clangErrSize = *errSize;
       }
-      p = gbe_program_new_from_llvm(llName.c_str(), stringSize,
+      p = gbe_program_new_from_llvm(deviceID, llName.c_str(), stringSize,
                                     err, errSize, optLevel);
       if (err != NULL)
         *errSize += clangErrSize;
diff --git a/backend/src/backend/program.h b/backend/src/backend/program.h
index c22793e..d90ada3 100644
--- a/backend/src/backend/program.h
+++ b/backend/src/backend/program.h
@@ -112,7 +112,8 @@ typedef void (gbe_kernel_get_image_data_cb)(gbe_kernel gbeKernel, ImageInfo *ima
 extern gbe_kernel_get_image_data_cb *gbe_kernel_get_image_data;
 
 /*! Create a new program from the given source code (zero terminated string) */
-typedef gbe_program (gbe_program_new_from_source_cb)(const char *source,
+typedef gbe_program (gbe_program_new_from_source_cb)(uint32_t deviceID,
+                                                     const char *source,
                                                      size_t stringSize,
                                                      const char *options,
                                                      char *err,
@@ -120,7 +121,7 @@ typedef gbe_program (gbe_program_new_from_source_cb)(const char *source,
 extern gbe_program_new_from_source_cb *gbe_program_new_from_source;
 
 /*! Create a new program from the given blob */
-typedef gbe_program (gbe_program_new_from_binary_cb)(const char *binary, size_t size);
+typedef gbe_program (gbe_program_new_from_binary_cb)(uint32_t deviceID, const char *binary, size_t size);
 extern gbe_program_new_from_binary_cb *gbe_program_new_from_binary;
 
 /*! Serialize a program to a bin */
@@ -128,7 +129,8 @@ typedef size_t (gbe_program_serialize_to_binary_cb)(gbe_program program, char **
 extern gbe_program_serialize_to_binary_cb *gbe_program_serialize_to_binary;
 
 /*! Create a new program from the given LLVM file */
-typedef gbe_program (gbe_program_new_from_llvm_cb)(const char *fileName,
+typedef gbe_program (gbe_program_new_from_llvm_cb)(uint32_t deviceID,
+                                                   const char *fileName,
                                                    size_t string_size,
                                                    char *err,
                                                    size_t *err_size,
diff --git a/backend/src/gbe_bin_generater.cpp b/backend/src/gbe_bin_generater.cpp
index f813775..1d97f01 100644
--- a/backend/src/gbe_bin_generater.cpp
+++ b/backend/src/gbe_bin_generater.cpp
@@ -192,7 +192,9 @@ void program_build_instance::serialize_program(void) throw(int)
 
 void program_build_instance::build_program(void) throw(int)
 {
-    gbe_program opaque = gbe_program_new_from_source(code, 0, build_opt.c_str(), NULL, NULL);
+    // FIXME, we need to find a graceful way to generate internal binaries for difference
+    // devices.
+    gbe_program opaque = gbe_program_new_from_source(0, code, 0, build_opt.c_str(), NULL, NULL);
     if (!opaque)
         throw FILE_BUILD_FAILED;
 
diff --git a/src/cl_program.c b/src/cl_program.c
index 8ae3aa7..184d6b5 100644
--- a/src/cl_program.c
+++ b/src/cl_program.c
@@ -225,7 +225,7 @@ cl_program_create_from_llvm(cl_context ctx,
   INVALID_VALUE_IF (file_name == NULL);
 
   program = cl_program_new(ctx);
-  program->opaque = gbe_program_new_from_llvm(file_name, program->build_log_max_sz, program->build_log, &program->build_log_sz, 1);
+  program->opaque = gbe_program_new_from_llvm(ctx->device->vendor_id, file_name, program->build_log_max_sz, program->build_log, &program->build_log_sz, 1);
   if (UNLIKELY(program->opaque == NULL)) {
     err = CL_INVALID_PROGRAM;
     goto error;
@@ -326,7 +326,7 @@ cl_program_build(cl_program p, const char *options)
   }
 
   if (p->source_type == FROM_SOURCE) {
-    p->opaque = gbe_program_new_from_source(p->source, p->build_log_max_sz, options, p->build_log, &p->build_log_sz);
+    p->opaque = gbe_program_new_from_source(p->ctx->device->vendor_id, p->source, p->build_log_max_sz, options, p->build_log, &p->build_log_sz);
     if (UNLIKELY(p->opaque == NULL)) {
       if (p->build_log_sz > 0 && strstr(p->build_log, "error: error reading 'options'"))
         err = CL_INVALID_BUILD_OPTIONS;
@@ -339,7 +339,7 @@ cl_program_build(cl_program p, const char *options)
     TRY (cl_program_load_gen_program, p);
     p->source_type = FROM_LLVM;
   } else if (p->source_type == FROM_BINARY) {
-    p->opaque = gbe_program_new_from_binary(p->binary, p->binary_sz);
+    p->opaque = gbe_program_new_from_binary(p->ctx->device->vendor_id, p->binary, p->binary_sz);
     if (UNLIKELY(p->opaque == NULL)) {
       err = CL_BUILD_PROGRAM_FAILURE;
       goto error;
-- 
1.8.3.2



More information about the Beignet mailing list