示例#1
0
void Kernel::setArgument(unsigned int index, TypedValue value)
{
  assert(index < m_function->arg_size());

  const llvm::Value *argument = getArgument(index);

  // Deallocate existing argument
  if (m_values.count(argument))
  {
    delete[] m_values[argument].data;
  }

#if LLVM_VERSION >= 40
  if (getArgumentTypeName(index).str() == "sampler_t")
  {
    // Get an llvm::ConstantInt that represents the sampler value
    llvm::Type *i32 = llvm::Type::getInt32Ty(m_program->getLLVMContext());
    llvm::Constant *samplerValue = llvm::ConstantInt::get(i32, value.getSInt());

    // A sampler argument is a pointer to the llvm::ConstantInt value
    TypedValue sampler;
    sampler.size = sizeof(size_t);
    sampler.num = 1;
    sampler.data = new unsigned char[sizeof(size_t)];
    sampler.setPointer((size_t)samplerValue);

    m_values[argument] = sampler;
  }
  else
#endif
  {
    m_values[argument] = value.clone();
  }
}
示例#2
0
void Program::allocateProgramScopeVars()
{
  deallocateProgramScopeVars();

  Memory *globalMemory = m_context->getGlobalMemory();

  // Create the pointer values for each global variable
  llvm::Module::const_global_iterator itr;
  for (itr = m_module->global_begin(); itr != m_module->global_end(); itr++)
  {
    unsigned addrspace = itr->getType()->getPointerAddressSpace();
    if (addrspace != AddrSpaceGlobal && addrspace != AddrSpaceConstant)
      continue;

    // Allocate global variable
    const llvm::Type *type = itr->getType()->getPointerElementType();
    size_t size = getTypeSize(type);
    size_t ptr = globalMemory->allocateBuffer(size);
    m_totalProgramScopeVarSize += size;

    // Create pointer value
    TypedValue ptrValue =
    {
      sizeof(size_t), 1, new uint8_t[sizeof(size_t)]
    };
    ptrValue.setPointer(ptr);
    m_programScopeVars[&*itr] = ptrValue;
  }

  try
  {
    // Initialize global variables
    for (auto itr  = m_programScopeVars.begin();
              itr != m_programScopeVars.end();
              itr++)
    {
      auto var = llvm::cast<llvm::GlobalVariable>(itr->first);
      const llvm::Constant *initializer = var->getInitializer();
      if (!initializer)
        continue;

      size_t varptr = itr->second.getPointer();
      if (initializer->getType()->getTypeID() == llvm::Type::PointerTyID)
      {
        size_t ptr = resolveConstantPointer(initializer, m_programScopeVars);
        globalMemory->store((uint8_t*)&ptr, varptr, sizeof(size_t));
      }
      else
      {
        size_t size = getTypeSize(initializer->getType());
        uint8_t *data = new uint8_t[size];
        getConstantData((uint8_t*)data, (const llvm::Constant*)initializer);
        globalMemory->store(data, varptr, size);
        delete[] data;
      }
    }
  }
  catch (FatalError& err)
  {
    cerr << endl << "OCLGRIND FATAL ERROR "
         << "(" << err.getFile() << ":" << err.getLine() << ")"
         << endl << err.what()
         << endl << "When initializing program scope global variables"
         << endl;
  }
}
示例#3
0
WorkItem::WorkItem(const KernelInvocation *kernelInvocation,
                   WorkGroup *workGroup, Size3 lid)
  : m_context(kernelInvocation->getContext()),
    m_kernelInvocation(kernelInvocation),
    m_workGroup(workGroup)
{
  m_localID = lid;

  // Compute global ID
  Size3 groupID = workGroup->getGroupID();
  Size3 groupSize = workGroup->getGroupSize();
  Size3 globalOffset = kernelInvocation->getGlobalOffset();
  m_globalID.x = lid.x + groupID.x*groupSize.x + globalOffset.x;
  m_globalID.y = lid.y + groupID.y*groupSize.y + globalOffset.y;
  m_globalID.z = lid.z + groupID.z*groupSize.z + globalOffset.z;

  Size3 globalSize = kernelInvocation->getGlobalSize();
  m_globalIndex = (m_globalID.x +
                  (m_globalID.y +
                   m_globalID.z*globalSize.y) * globalSize.x);

  const Kernel *kernel = kernelInvocation->getKernel();

  // Load interpreter cache
  m_cache = kernel->getProgram()->getInterpreterCache(kernel->getFunction());

  // Set initial number of values to store based on cache
  m_values.resize(m_cache->getNumValues());

  m_privateMemory = new Memory(AddrSpacePrivate, sizeof(size_t)==8 ? 32 : 16,
                               m_context);

  // Initialise kernel arguments and global variables
  for (auto value  = kernel->values_begin();
            value != kernel->values_end();
            value++)
  {
    pair<unsigned,unsigned> size = getValueSize(value->first);
    TypedValue v = {
      size.first,
      size.second,
      m_pool.alloc(size.first*size.second)
    };

    const llvm::Type *type = value->first->getType();
    if (type->isPointerTy() &&
        type->getPointerAddressSpace() == AddrSpacePrivate)
    {
      size_t sz = value->second.size*value->second.num;
      v.setPointer(m_privateMemory->allocateBuffer(sz, 0, value->second.data));
    }
    else if (type->isPointerTy() &&
             type->getPointerAddressSpace() == AddrSpaceLocal)
    {
      v.setPointer(m_workGroup->getLocalMemoryAddress(value->first));
    }
    else
    {
      memcpy(v.data, value->second.data, v.size*v.num);
    }

    setValue(value->first, v);
  }

  // Initialize interpreter state
  m_state    = READY;
  m_position = new Position;
  m_position->hasBegun = false;
  m_position->prevBlock = NULL;
  m_position->nextBlock = NULL;
  m_position->currBlock = &*kernel->getFunction()->begin();
  m_position->currInst = m_position->currBlock->begin();
}