Пример #1
0
llvm::Module *ClangCompiler::Compile(const string &source,
                                     LLVMContext *context) const
{
    // write the source to a temporary file and invoke the compiler
    string temp_tmpl = ".tmp_XXXXXX";
    const char *tmpfile = UniqueFilename(temp_tmpl);
    //const char *tmpfile = "temp.c";

    SourceToFile(tmpfile, source);

    FrontendOptions &opts = invocation_->getFrontendOpts();
#if CLANG_VERSION_MAJOR == 3
#   if CLANG_VERSION_MINOR == 0
    opts.Inputs.clear();    // clear any old inputs
    opts.Inputs.push_back(make_pair(IK_C, tmpfile));
#   elif CLANG_VERSION_MINOR == 5
    opts.Inputs.clear();    // clear any old inputs
    opts.Inputs.push_back(FrontendInputFile(tmpfile, IK_C));
#   endif
#endif
    
    // compiler_->setInvocation(invocation_.get());
    compiler_->setInvocation(invocation_);

    // Setup diagnostics for the compilation process itself
#if CLANG_VERSION_MAJOR == 3
#   if CLANG_VERSION_MINOR == 0
    const char *const dummy_argv[] = { "" };
    compiler_->createDiagnostics(1, dummy_argv);
#   elif CLANG_VERSION_MINOR == 5
    compiler_->createDiagnostics();
#   endif
#endif

    if (!compiler_->hasDiagnostics()) {
        *log_stream_ << "createDiagnostics() failed\n";
        return 0;
    }

    // Compile and emit LLVM IR
    // OwningPtr<CodeGenAction> llvm_codegen(new EmitLLVMOnlyAction(context));
    CodeGenAction *llvm_codegen(new EmitLLVMOnlyAction(context));
    if (!compiler_->ExecuteAction(*llvm_codegen)) {
        *log_stream_ << "compilation failed: "
                     << "generated source is in " << tmpfile << "\n";
        return 0;
    }

    // Remove input file and return the compiled module
    if (!keep_temporaries_)
        RemoveFile(tmpfile);
    return llvm_codegen->takeModule();
}
Пример #2
0
void
pocl_basic_run 
(void *data, 
 _cl_command_node* cmd)
{
  struct data *d;
  int error;
  const char *module_fn;
  char command[COMMAND_LENGTH];
  char workgroup_string[WORKGROUP_STRING_LENGTH];
  unsigned device;
  struct pocl_argument *al;
  size_t x, y, z;
  unsigned i;
  pocl_workgroup w;
  char* tmpdir = cmd->command.run.tmp_dir;
  cl_kernel kernel = cmd->command.run.kernel;
  struct pocl_context *pc = &cmd->command.run.pc;

  assert (data != NULL);
  d = (struct data *) data;

  module_fn = llvm_codegen (tmpdir);
      
  d->current_dlhandle = lt_dlopen (module_fn);
  if (d->current_dlhandle == NULL)
    {
      printf ("pocl error: lt_dlopen(\"%s\") failed with '%s'.\n", module_fn, lt_dlerror());
      printf ("note: missing symbols in the kernel binary might be reported as 'file not found' errors.\n");
      abort();
    }


  d->current_kernel = kernel;

  /* Find which device number within the context correspond
     to current device.  */
  for (i = 0; i < kernel->context->num_devices; ++i)
    {
      if (kernel->context->devices[i]->data == data)
        {
          device = i;
          break;
        }
    }

  snprintf (workgroup_string, WORKGROUP_STRING_LENGTH,
            "_%s_workgroup", kernel->function_name);
  
  w = (pocl_workgroup) lt_dlsym (d->current_dlhandle, workgroup_string);
  if (w == NULL)
    {
      printf("pocl error: could not load the work-group function '%s' in module '%s'.\n",
	     workgroup_string, module_fn);
      abort();
    }
  free ((void*) module_fn);

  void *arguments[kernel->num_args + kernel->num_locals];

  /* Process the kernel arguments. Convert the opaque buffer
     pointers to real device pointers, allocate dynamic local 
     memory buffers, etc. */
  for (i = 0; i < kernel->num_args; ++i)
    {
      al = &(cmd->command.run.arguments[i]);
      if (kernel->arg_is_local[i])
        {
          arguments[i] = malloc (sizeof (void *));
          *(void **)(arguments[i]) = pocl_basic_malloc(data, 0, al->size, NULL);
        }
      else if (kernel->arg_is_pointer[i])
        {
          /* It's legal to pass a NULL pointer to clSetKernelArguments. In 
             that case we must pass the same NULL forward to the kernel.
             Otherwise, the user must have created a buffer with per device
             pointers stored in the cl_mem. */
          if (al->value == NULL)
            {
              arguments[i] = malloc (sizeof (void *));
              *(void **)arguments[i] = NULL;
            }
          else
            arguments[i] = &((*(cl_mem *) (al->value))->device_ptrs[device]);
        }
      else if (kernel->arg_is_image[i])
        {
          dev_image2d_t di;      
          cl_mem mem = *(cl_mem*)al->value;
          di.data = &((*(cl_mem *) (al->value))->device_ptrs[device]);
          di.data = ((*(cl_mem *) (al->value))->device_ptrs[device]);
          di.width = mem->image_width;
          di.height = mem->image_height;
          di.rowpitch = mem->image_row_pitch;
          di.order = mem->image_channel_order;
          di.data_type = mem->image_channel_data_type;
          void* devptr = pocl_basic_malloc(data, 0, sizeof(dev_image2d_t), NULL);
          arguments[i] = malloc (sizeof (void *));
          *(void **)(arguments[i]) = devptr; 
          pocl_basic_write (data, &di, devptr, sizeof(dev_image2d_t));
        }
      else if (kernel->arg_is_sampler[i])
        {
          dev_sampler_t ds;
          
          arguments[i] = malloc (sizeof (void *));
          *(void **)(arguments[i]) = pocl_basic_malloc(data, 0, sizeof(dev_sampler_t), NULL);
          pocl_basic_write (data, &ds, *(void**)arguments[i], sizeof(dev_sampler_t));
        }
      else
        {
          arguments[i] = al->value;
        }
    }
  for (i = kernel->num_args;
       i < kernel->num_args + kernel->num_locals;
       ++i)
    {
      al = &(cmd->command.run.arguments[i]);
      arguments[i] = malloc (sizeof (void *));
      *(void **)(arguments[i]) = pocl_basic_malloc(data, 0, al->size, NULL);
    }

  for (z = 0; z < pc->num_groups[2]; ++z)
    {
      for (y = 0; y < pc->num_groups[1]; ++y)
        {
          for (x = 0; x < pc->num_groups[0]; ++x)
            {
              pc->group_id[0] = x;
              pc->group_id[1] = y;
              pc->group_id[2] = z;

              w (arguments, pc);

            }
        }
    }
  for (i = 0; i < kernel->num_args; ++i)
    {
      if (kernel->arg_is_local[i])
        pocl_basic_free(data, 0, *(void **)(arguments[i]));
    }
  for (i = kernel->num_args;
       i < kernel->num_args + kernel->num_locals;
       ++i)
    pocl_basic_free(data, 0, *(void **)(arguments[i]));
}