繁体   English   中英

caffe2张量 <CUDAContext> 作业,构造或复制

[英]caffe2 Tensor<CUDAContext> assignment, construction or copy

这是一个长镜头,如果您认为问题过于局限,请投票关闭。 我已经搜索了caffe2 github存储库,打开了一个问题,问了同样的问题,在caffe2_ccp_tutorials存储库中打开了另一个问题,因为它的作者似乎最了解它,阅读了caffe2 :: Tensorcaffe2 :: CUDAContext上的doxygen文档,甚至通过了caffe2 源代码 ,尤其是tensor.hcontext_gpu.hcontext_gpu.cc

我知道,当前caffe2不允许将设备内存复制到张量 我愿意扩展该库并提出请求,以实现此目的。 我这样做的原因是,我使用在设备内存上运行的cv::cuda::*方法进行所有图像预处理,因此,我认为在gpu上进行预处理显然是一个问题,只能下载结果返回到主机,然后将其从主机重新上传到网络。

查看Tensor<Context>的构造函数,我可以看到也许只有

template<class SrcContext , class ContextForCopy > 
Tensor (const Tensor< SrcContext > &src, ContextForCopy *context)

也许可以实现我想要的,但是我不知道如何设置<ContextForCopy>并将其用于构造。

此外,我知道我可以构造张量与正确的尺寸,然后使用可能

template <typename T>
T* mutable_data()

我可以分配/复制数据。 数据本身存储在std::vector<cv::cuda::GpuMat ,因此我将不得不对其进行迭代,然后使用cuda::PtrStepSzcuda::PtrStep来访问基础设备分配的数据。 那就是我需要复制/分配到caffe2::Tensor<CUDAContext>的相同数据。

自从我看到过示例之后,我一直在尝试找出Tensor<CPUContext>在内部如何复制到Tensor<CUDAContext> ,但是我无法弄清楚,尽管我认为使用的方法是CopyFrom 如前所述,通常的示例是从CPU复制到GPU:

TensorCPU tensor_cpu(...);
TensorCUDA tensor_cuda = workspace.CreateBlob("input")->GetMutable<TensorCUDA>();
tensor_cuda->ResizeLike(tensor_cpu);
tensor_cuda->ShareData(tensor_cpu);

我很惊讶,还没有人完成这项任务,而简短的搜索仅产生一个未解决的问题 ,作者(@peterneher)或多或少地在问同样的事情。

我设法弄清楚了。 最简单的方法是告诉OpenCV使用哪个内存位置。 这可以通过使用cv::cuda::GpuMat构造函数第7和第8重载来完成,如下所示:

cv::cuda::GpuMat::GpuMat(int    rows,
                         int    cols,
                         int    type,
                         void *     data,
                         size_t     step = Mat::AUTO_STEP 
                        )       

cv::cuda::GpuMat::GpuMat(Size   size,
                         int    type,
                         void *     data,
                         size_t     step = Mat::AUTO_STEP 
                        )       

这样做意味着已经预先声明并分配caffe2::TensorCUDA

std::vector<caffe2::TIndex> dims({1, 3, 224, 224});
caffe2::TensorCUDA tensor;
auto ptr = tensor.mutable_data<float>();
cv::cuda::GpuMat matrix(224, 224, CV_32F, ptr);

例如,使用cv::cuda::split处理3通道BGR浮点矩阵:

cv::cuda::GpuMat mfloat;
// TODO: put your BGR float data in `mfloat`
auto ptr = tensor.mutable_data<float>();
size_t width = mfloat.cols * mfloat.rows;
std::vector<cv::cuda::GpuMat> input_channels {
    cv::cuda::GpuMat(mfloat.rows, mfloat.cols, CV_32F, &ptr[0]),
    cv::cuda::GpuMat(mfloat.rows, mfloat.cols, CV_32F, &ptr[width]),
    cv::cuda::GpuMat(mfloat.rows, mfloat.cols, CV_32F, &ptr[width * 2])
};
cv::cuda::split(mfloat, input_channels);

希望这会帮助任何陷入Caffe2 C ++方面的人。

注意caffe2::Predictor不能与caffe2::TensorCUDA ,而必须手动传播张量。 有关更多信息,请访问caffe2_cpp_tutorial mnist.cc

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM