我正在开发一个开源项目“粉末玩具”,并在msvc下编译它。运行正常。但是当我在air.h中包含一个新标题时,编译会产生如下错误:
“GetUserNameA!不是GameController.cpp文件中的'SaveInfo'的成员。
和
语法错误:BitmapBrush.h文件中的'::'。 --->指向最小 - 最大窗口。
两个文件都不受影响,与我添加的标题没有任何共同之处:
Aux_cl.h --->添加到air.h的开头
这个标题只有opencl标题,而powdertoy在任何其他cpp / h文件中都没有它们。
我做错了什么? 如果我删除了Aux_cl的包含,那么即使使用Aux_cl中的opencl绑定项目编译也很好(这不会绑定到任何东西,只是我认为是单独编译的)
编辑:当我在这些错误点之前添加“#undef min”和“#undef GetUserName”时,它会编译文件,我想知道如果没有我之前包含的头文件它是如何工作的。
Edit2:我应该在#undef blabla之后的函数之后添加#def blabla吗?
这是
Air.h:
#ifndef AIR_H
#define AIR_H
#include "Config.h"
#include "Aux_cl.h"
class Simulation;
class Air
{
public:
Simulation & sim;
int airMode;
float ambientAirTemp;
Aux_cl *gpu;
//Arrays from the simulation
unsigned char (*bmap)[XRES/CELL];
unsigned char (*emap)[XRES/CELL];
float (*fvx)[XRES/CELL];
float (*fvy)[XRES/CELL];
//
float vx[YRES/CELL][XRES/CELL];
float ovx[YRES/CELL][XRES/CELL];
float vy[YRES/CELL][XRES/CELL];
float ovy[YRES/CELL][XRES/CELL];
float pv[YRES/CELL][XRES/CELL];
float opv[YRES/CELL][XRES/CELL];
float hv[YRES/CELL][XRES/CELL];
float ohv[YRES/CELL][XRES/CELL]; // Ambient Heat
unsigned char bmap_blockair[YRES/CELL][XRES/CELL];
unsigned char bmap_blockairh[YRES/CELL][XRES/CELL];
float kernel[9];
void make_kernel(void);
void update_airh(void);
void update_air(void);
void Clear();
void ClearAirH();
void Invert();
Air(Simulation & sim);
};
#endif
Aux_cl.h:
#pragma once
#define __CL_ENABLE_EXCEPTIONS
#include<CL\opencl.h>
#include<CL\cl.hpp>
#include<CL\cl.h>
#include"ClKernelFactory.h" // this has nothing but string variables and simple function. No other includes about windows or powder toy
#define FIRST_COMPUTE_DEVICE 0
/*
Simple compute helper class for your heavy work loads.
Uses OpenCL 1.2 headers so you may need an up-to-date CPU or an AMD-GPU for now.
Instances of this classes are different contexts and should be compiled serially.
Computation can be concurrent without fear.
Writer: Huseyin Tugrul BUYUKISIK
*/
class Aux_cl
{
public:
cl::Context *context;
std::vector<cl::Program::Sources> sources;
std::vector<cl::Program> programs;
std::vector<std::vector<cl::Device>> devicesCPU;
std::vector<std::vector<cl::Device>> devicesGPU;
cl::CommandQueue cq;
std::vector<cl::Buffer> buffers;
std::vector<cl::Memory> memories;
std::vector<cl::NDRange> globalRanges;
std::vector<cl::NDRange> localRanges;
std::vector<cl::NDRange> referenceRanges;
std::vector<std::string> kernelFunctionsToBeCompiled;
std::vector<std::string> kernelNames;
std::vector<std::string> bufferNames;
std::vector<cl::Kernel> kernelFunctions;
std::vector<std::pair<std::vector<int>,int>> bufferTargetsForKernels; // {500}, {501, 502},{530} ... --> buffer ids
// 0,1,2,... --> kernel ids
std::vector<std::pair<int,std::vector<std::string>>> bufferDefinitions;
std::vector<std::pair<int,std::string>> kernelDefinitions;
std::vector<cl::Platform> platforms;
cl_context_properties *context_properties;
std::string CPU_GPU; //"gpu" "GPU" "graphics" "GRAPHICS" "cpu" "CPU"
int kernelId;
int bufferId;
int numberOfCPU;
int numberOfGPU;
int first_CPU_platform;
int first_CPU_device;
int first_GPU_platform;
int first_GPU_device;
int second_CPU_platform;
int second_CPU_device;
int second_GPU_platform;
int second_GPU_device;
int which_one;
static const int FIRST=0, SECOND=1, THIRD=2, FOURTH=3, OMG=4;
Aux_cl(std::string gpu_or_cpu, int whichOne)
{
which_one=whichOne;
CPU_GPU=gpu_or_cpu;
kernelId=0;
bufferId=0;
numberOfGPU=0;
numberOfCPU=0;
cl::Platform::get(&platforms);
for(int i=0;i<platforms.size();i++)
{
devicesCPU.push_back(std::vector<cl::Device>()); // one device list for each platform (AMD, NVIDIA, INTEL, ...)
}
for(int i=0;i<platforms.size();i++)
{
devicesGPU.push_back(std::vector<cl::Device>()); // one device list for each platform (AMD, NVIDIA, INTEL, ...)
}
//selecting the platform that has a cpu or gpu specified in construction
for(int i=0;i<platforms.size();i++)
{
platforms[i].getDevices(CL_DEVICE_TYPE_CPU,&devicesCPU[i]);
}
//selecting the platform that has a cpu or gpu specified in construction
for(int i=0;i<platforms.size();i++)
{
platforms[i].getDevices(CL_DEVICE_TYPE_GPU,&devicesGPU[i]);
}
//searching device lists for a gpu or cpu (as selected in construction)
for(int i=0;i<platforms.size();i++)
{
bool notFoundYet=true;
bool notFoundYet2=true;
if(devicesCPU[i].size()>0)
for(int j=0;j<devicesCPU[i].size();j++)
{
if(notFoundYet)
{
first_CPU_platform=i;
first_CPU_device=j;
notFoundYet=false;
}
if((!notFoundYet)&&(notFoundYet2))
{
second_CPU_platform=i;
second_CPU_device=j;
notFoundYet2=false;
}
numberOfCPU++;
}
}
//searching device lists for a gpu or cpu (as selected in construction)
for(int i=0;i<platforms.size();i++)
{
bool notFoundYet=true;bool notFoundYet2=true;
if(devicesGPU[i].size()>0)
for(int j=0;j<devicesCPU[i].size();j++)
{
if(notFoundYet)
{
first_GPU_platform=i;
first_GPU_device=j;
notFoundYet=false;
}
if((!notFoundYet)&&(notFoundYet2))
{
second_CPU_platform=i;
second_CPU_device=j;
notFoundYet2=false;
}
numberOfGPU++;
}
}
};
void AddKernelFromFactory(KernelIngredients ki)
{
AddKernelToPool(ki.bodyOfKernel, ki.nameOfKernel,
ki.globalX,ki.globalY,
ki.localX,ki.localY);
}
void AddKernelToPool(std::string KernelItself, std::string KernelName,
int GlobalRangeX,int GlobalRangeY,
int LocalRangeX,int LocalRangeY)
{
if(GlobalRangeY!=0)
{
kernelFunctionsToBeCompiled.push_back(KernelItself);
kernelNames.push_back(KernelName);
globalRanges.push_back(cl::NDRange(GlobalRangeX,GlobalRangeY));
localRanges.push_back(cl::NDRange(LocalRangeX,LocalRangeY));
referenceRanges.push_back(cl::NDRange(0,0));
kernelDefinitions.push_back(std::pair<int,std::string>(kernelId,KernelName));
kernelId++;
}
else
{
kernelFunctionsToBeCompiled.push_back(KernelItself);
kernelNames.push_back(KernelName);
globalRanges.push_back(cl::NDRange(GlobalRangeX));
localRanges.push_back(cl::NDRange(LocalRangeX));
referenceRanges.push_back(cl::NDRange(0));
kernelDefinitions.push_back(std::pair<int,std::string>(kernelId,KernelName));
kernelId++;
}
};
void AddBufferToPool(std::string nameOfBuffer,std::string typeOfBuffer, int sizeOfBuffer)
{
// 0,{"a","float","8192"}
std::vector<std::string> BufferNameTypeSize;
BufferNameTypeSize.push_back(nameOfBuffer);
BufferNameTypeSize.push_back(typeOfBuffer);
BufferNameTypeSize.push_back(std::to_string(sizeOfBuffer));
bufferDefinitions.push_back(std::pair<int,std::vector<std::string>>(bufferId,BufferNameTypeSize));
bufferNames.push_back(BufferNameTypeSize[0]);
bufferId++;
}
void WireBuffersToSingleKernel(std::vector<std::string> buffers, std::string theKernel )
{
std::vector<int> bufferL;
int index=-1;
for(int i=0;i<buffers.size();i++)
{
for(int j=0;j<bufferDefinitions.size();j++)
{
if(bufferDefinitions[j].second[0]==(buffers[i]))
{
bufferL.push_back(bufferDefinitions[j].first);
}
}
for(int k=0;k<kernelDefinitions.size();k++)
{
if(kernelDefinitions[k].second==(theKernel))
{
index=kernelDefinitions[k].first;
}
}
}
bufferTargetsForKernels.push_back(std::pair<std::vector<int>,int>(bufferL,index));
// buffers {23,33,10,1,40} for the kernel {3} as a pair
}
void compile()
{
if(which_one==FIRST)
{
//clGetPlatformIDs(1,&platform_id,NULL);
if((CPU_GPU==("CPU"))||(CPU_GPU==("cpu")))
{
cl_context_properties properties[] = { CL_CONTEXT_PLATFORM, (cl_context_properties)(platforms[first_CPU_platform])(), 0};
context=new cl::Context(CL_DEVICE_TYPE_CPU, properties);
}
if((CPU_GPU==("GPU"))||(CPU_GPU==("gpu")))
{
cl_context_properties properties[] = { CL_CONTEXT_PLATFORM, (cl_context_properties)(platforms[first_GPU_platform])(), 0};
context=new cl::Context(CL_DEVICE_TYPE_GPU, properties);
}
}
if(which_one==SECOND)
{
//clGetPlatformIDs(1,&platform_id,NULL);
if((CPU_GPU==("CPU"))||(CPU_GPU==("cpu")))
{
cl_context_properties properties[] = { CL_CONTEXT_PLATFORM, (cl_context_properties)(platforms[second_CPU_platform])(), 0};
context=new cl::Context(CL_DEVICE_TYPE_CPU, properties);
}
if((CPU_GPU==("GPU"))||(CPU_GPU==("gpu")))
{
cl_context_properties properties[] = { CL_CONTEXT_PLATFORM, (cl_context_properties)(platforms[second_GPU_platform])(), 0};
context=new cl::Context(CL_DEVICE_TYPE_GPU, properties);
}
}
/*
for(int i=0;i<platforms.size();i++)
{
devices[i]=context[0].getInfo<CL_CONTEXT_DEVICES>(); // device lists are created
}
*/
if(which_one==FIRST)
{
for(int i=0;i<kernelFunctionsToBeCompiled.size();i++)
{
sources.push_back(cl::Program::Sources());
sources[i].push_back(std::make_pair(kernelFunctionsToBeCompiled[i].data(),kernelFunctionsToBeCompiled[i].length()));
programs.push_back(cl::Program(context[0],sources[i]));
if((CPU_GPU==("CPU"))||(CPU_GPU==("cpu")))
{
programs[i].build(devicesCPU[first_CPU_platform]);
}
if((CPU_GPU==("GPU"))||(CPU_GPU==("gpu")))
{
programs[i].build(devicesGPU[first_GPU_platform]);
}
kernelFunctions.push_back(cl::Kernel(programs[i],kernelNames[i].data()));
}
if((CPU_GPU==("CPU"))||(CPU_GPU==("cpu")))
{
cq=cl::CommandQueue(context[0],devicesCPU[first_CPU_platform][first_CPU_device]);
}
if((CPU_GPU==("GPU"))||(CPU_GPU==("gpu")))
{
cq=cl::CommandQueue(context[0],devicesGPU[first_GPU_platform][first_GPU_device]);
}
}
if(which_one==SECOND)
{
for(int i=0;i<kernelFunctionsToBeCompiled.size();i++)
{
sources.push_back(cl::Program::Sources());
sources[i].push_back(std::make_pair(kernelFunctionsToBeCompiled[i].data(),kernelFunctionsToBeCompiled[i].length()));
programs.push_back(cl::Program(context[0],sources[i]));
if((CPU_GPU==("CPU"))||(CPU_GPU==("cpu")))
{
programs[i].build(devicesCPU[second_CPU_platform]);
}
if((CPU_GPU==("GPU"))||(CPU_GPU==("gpu")))
{
programs[i].build(devicesGPU[second_GPU_platform]);
}
kernelFunctions.push_back(cl::Kernel(programs[i],kernelNames[i].data()));
}
if((CPU_GPU==("CPU"))||(CPU_GPU==("cpu")))
{
cq=cl::CommandQueue(context[0],devicesCPU[second_CPU_platform][second_CPU_device]);
}
if((CPU_GPU==("GPU"))||(CPU_GPU==("gpu")))
{
cq=cl::CommandQueue(context[0],devicesGPU[second_GPU_platform][second_GPU_device]);
}
}
for(int i=0;i<bufferDefinitions.size();i++)
{
int sizeOfBuffer=std::stoi(bufferDefinitions[i].second[2]);
if(bufferDefinitions[i].second[1]=="float")
{
buffers.push_back(cl::Buffer(context[0],CL_MEM_READ_WRITE,sizeof(cl_float)*sizeOfBuffer));
}
if(bufferDefinitions[i].second[1]=="int")
{
buffers.push_back(cl::Buffer(context[0],CL_MEM_READ_WRITE,sizeof(cl_int)*sizeOfBuffer));
}
if(bufferDefinitions[i].second[1]=="double")
{
buffers.push_back(cl::Buffer(context[0],CL_MEM_READ_WRITE,sizeof(cl_double)*sizeOfBuffer));
}
if(bufferDefinitions[i].second[1]=="long")
{
buffers.push_back(cl::Buffer(context[0],CL_MEM_READ_WRITE,sizeof(cl_long)*sizeOfBuffer));
}
if(bufferDefinitions[i].second[1]=="char")
{
buffers.push_back(cl::Buffer(context[0],CL_MEM_READ_WRITE,sizeof(cl_char)*sizeOfBuffer));
}
}
for(int i=0;i<bufferTargetsForKernels.size();i++)
{
for(int j=0;j<bufferTargetsForKernels[i].first.size();j++)
{
kernelFunctions[bufferTargetsForKernels[i].second].setArg(j,buffers[bufferTargetsForKernels[i].first[j]]);
}
}
}
void SelectClBuffersToWriteOnThem()
{
}
void SelectClBuffersToReadFromThem()
{
}
void WriteToClFromCPP(std::string clArrayName,float *arrayCPP)
{
for(int i=0;i<buffers.size();i++)
{
if(bufferNames[i]==clArrayName)
{
cq.finish();
cq.enqueueWriteBuffer(buffers[i],CL_TRUE,0,sizeof(cl_float)*(std::atoi(bufferDefinitions[i].second[2].data())),arrayCPP);
cq.finish();
}
}
}
void WriteToClFrom2DCPP(std::string clArrayName,static float *arrayCPP) // 2D array = contiguous?
{
for(int i=0;i<buffers.size();i++)
{
if(bufferNames[i]==clArrayName)
{
cq.finish();
cq.enqueueWriteBuffer(buffers[i],CL_TRUE,0,sizeof(cl_float)*(std::atoi(bufferDefinitions[i].second[2].data())), arrayCPP);
cq.finish();
}
}
}
void WriteToClFrom2DCPP(std::string clArrayName,static char *arrayCPP) // 2D array = contiguous?
{
for(int i=0;i<buffers.size();i++)
{
if(bufferNames[i]==clArrayName)
{
cq.finish();
cq.enqueueWriteBuffer(buffers[i],CL_TRUE,0,sizeof(cl_char)*(std::atoi(bufferDefinitions[i].second[2].data())), arrayCPP);
cq.finish();
}
}
}
void ReadFromClToCPP(std::string clArrayName, float *arrayCPP)
{
for(int i=0;i<buffers.size();i++)
{
if(bufferNames[i]==clArrayName)
{
cq.finish();
cq.enqueueReadBuffer(buffers[i],CL_TRUE,0,sizeof(cl_float)*(std::atoi(bufferDefinitions[i].second[2].data())),arrayCPP);
cq.finish();
}
}
}
void ReadFromClTo2DCPP(std::string clArrayName,static float *arrayCPP) // 2D arrays are contiguous?
{
for(int i=0;i<buffers.size();i++)
{
if(bufferNames[i]==clArrayName)
{
cq.finish();
cq.enqueueReadBuffer(buffers[i],CL_TRUE,0,sizeof(cl_float)*(std::atoi(bufferDefinitions[i].second[2].data())), arrayCPP);
cq.finish();
}
}
}
void ReadFromClTo2DCPP(std::string clArrayName,static char *arrayCPP) // 2D arrays are contiguous?
{
for(int i=0;i<buffers.size();i++)
{
if(bufferNames[i]==clArrayName)
{
cq.finish();
cq.enqueueReadBuffer(buffers[i],CL_TRUE,0,sizeof(cl_char)*(std::atoi(bufferDefinitions[i].second[2].data())), arrayCPP);
cq.finish();
}
}
}
std::vector<int> computeList;
void MakeKernelListToRun(std::vector<std::string> listOfKernels)
{
computeList.clear();
for(int j=0;j<listOfKernels.size();j++)
{
for(int i=0;i<kernelNames.size();i++)
{
if(listOfKernels[j]==kernelNames[i])
{
computeList.push_back(i);
}
}
}
}
void ComputeList()
{
for(int i=0;i<computeList.size();i++)
{
cq.enqueueNDRangeKernel(kernelFunctions[computeList[i]],referenceRanges[computeList[i]],globalRanges[computeList[i]],localRanges[computeList[i]]);
}
}
void Compute(std::string kernelName)
{
for(int i=0;i<kernelNames.size();i++)
{
if(kernelName==kernelNames[i])
{
cq.enqueueNDRangeKernel(kernelFunctions[i],referenceRanges[i],globalRanges[i],localRanges[i]);
}
}
}
void releaseClResources()
{
cq.finish();
// opencl c++ bindings wrapper deletes / releases automatically when of no use
}
~Aux_cl(void)
{
delete context;
};
};
上次修改:
在KernelIngredients.cpp中只有#include“KernelIngredients.h”
在KernelIngredients.h中没有包含
在ClKernelFactory.h中只有#include“KernelIngredients.h”
在ClKernelFactory.cpp中只有#include“ClKernelFactory.h”
在Aux_cl.cpp中只有#include“Aux_cl.h”
在Aux_cl.h中只有opencl包含(我希望这些内容不要使用与min()和GetUserName()冲突的窗口:S)
在Air.h中有#include“Aux_cl.h”和#include“ClKernelFactory.h”
答案 0 :(得分:1)
看起来通过air.h
间接包含的标题之一定义了一个与源中其他位置的符号名称冲突的宏。宏基本上定义了在编译器启动之前由预处理器执行的搜索替换操作。
举个例子:
/** header_1.h **/
void foo(){ std::cout << "Hello" << std::endl; }
/** header_2.h **/
#define foo bar
/** main.cpp **/
#include "header_1.h"
#include "header_2.h"
int main() {
foo();
}
编译main.cpp
会给您一个错误,即未定义方法bar
,因为预处理器替换了foo
之后出现的所有header_2.h
出现的bar
{{1}}。