49 lines
2.0 KiB
Plaintext
49 lines
2.0 KiB
Plaintext
#include "uyvy_converter.hpp"
|
|
#include "gpu_preprocess.hpp"
|
|
#include <cstring>
|
|
|
|
namespace cms {
|
|
__global__ void swapRedBlue(unsigned char* image,int count) {
|
|
int i=blockIdx.x*blockDim.x+threadIdx.x;
|
|
if(i>=count)return;
|
|
unsigned char r=image[3*i];image[3*i]=image[3*i+2];image[3*i+2]=r;
|
|
}
|
|
struct UyvyConverter::Impl {
|
|
int width,height;
|
|
cudaStream_t stream{};
|
|
unsigned char *uyvy{},*bgr{},*host{};
|
|
Impl(int w,int h):width(w),height(h) {
|
|
try {
|
|
CUDA_CHECK(cudaStreamCreateWithFlags(&stream,cudaStreamNonBlocking));
|
|
CUDA_CHECK(cudaMalloc(&uyvy,std::size_t(w)*h*2));
|
|
CUDA_CHECK(cudaMalloc(&bgr,std::size_t(w)*h*3));
|
|
CUDA_CHECK(cudaMallocHost(&host,std::size_t(w)*h*3));
|
|
} catch(...) {release();throw;}
|
|
}
|
|
~Impl(){release();}
|
|
void release() noexcept {
|
|
if(stream)cudaStreamSynchronize(stream);
|
|
if(uyvy)cudaFree(uyvy);
|
|
if(bgr)cudaFree(bgr);
|
|
if(host)cudaFreeHost(host);
|
|
if(stream)cudaStreamDestroy(stream);
|
|
}
|
|
};
|
|
UyvyConverter::UyvyConverter(int w,int h):impl_(std::make_unique<Impl>(w,h)){}
|
|
UyvyConverter::~UyvyConverter()=default;
|
|
std::shared_ptr<const BgrImage> UyvyConverter::convert(void const* data,std::size_t stride) {
|
|
auto& s=*impl_;
|
|
CUDA_CHECK(cudaMemcpy2DAsync(s.uyvy,s.width*2,data,stride,s.width*2,s.height,cudaMemcpyHostToDevice,s.stream));
|
|
nppCheck(nppiCbYCr422ToRGB_8u_C2C3R_Ctx(s.uyvy,s.width*2,s.bgr,s.width*3,{s.width,s.height},nppContext(s.stream)));
|
|
int pixels=s.width*s.height;
|
|
swapRedBlue<<<(pixels+255)/256,256,0,s.stream>>>(s.bgr,pixels);
|
|
CUDA_CHECK(cudaGetLastError());
|
|
CUDA_CHECK(cudaMemcpyAsync(s.host,s.bgr,std::size_t(pixels)*3,cudaMemcpyDeviceToHost,s.stream));
|
|
CUDA_CHECK(cudaStreamSynchronize(s.stream));
|
|
auto image=std::make_shared<BgrImage>();
|
|
image->width=s.width;image->height=s.height;image->stride=s.width*3;
|
|
image->pixels.assign(s.host,s.host+std::size_t(pixels)*3);
|
|
return image;
|
|
}
|
|
}
|