diff --git a/sunshine/crypto.cpp b/sunshine/crypto.cpp index 70a98289..398c8e09 100644 --- a/sunshine/crypto.cpp +++ b/sunshine/crypto.cpp @@ -187,10 +187,10 @@ x509_t x509(const std::string_view &x) { BIO_write(io.get(), x.data(), x.size()); - X509 *p = nullptr; + x509_t p; PEM_read_bio_X509(io.get(), &p, nullptr, nullptr); - return x509_t { p }; + return p; } pkey_t pkey(const std::string_view &k) { @@ -198,10 +198,10 @@ pkey_t pkey(const std::string_view &k) { BIO_write(io.get(), k.data(), k.size()); - EVP_PKEY *p = nullptr; + pkey_t p = nullptr; PEM_read_bio_PrivateKey(io.get(), &p, nullptr, nullptr); - return pkey_t { p }; + return p; } std::string pem(x509_t &x509) { diff --git a/sunshine/platform/windows/audio.cpp b/sunshine/platform/windows/audio.cpp index 0ba9a168..63369ccb 100644 --- a/sunshine/platform/windows/audio.cpp +++ b/sunshine/platform/windows/audio.cpp @@ -81,50 +81,43 @@ public: HRESULT status; - device_enum_t::pointer device_enum_p{}; status = CoCreateInstance( CLSID_MMDeviceEnumerator, nullptr, CLSCTX_ALL, IID_IMMDeviceEnumerator, - (void **) &device_enum_p); - device_enum.reset(device_enum_p); + (void **) &device_enum); - if (FAILED(status)) { + if(FAILED(status)) { BOOST_LOG(error) << "Couldn't create Device Enumerator [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - device_t::pointer device_p{}; - if(config::audio.sink.empty()) { status = device_enum->GetDefaultAudioEndpoint( eRender, eConsole, - &device_p); + &device); } else { std::wstring_convert, wchar_t> converter; auto wstring_device_id = converter.from_bytes(config::audio.sink); - status = device_enum->GetDevice(wstring_device_id.c_str(), &device_p); + status = device_enum->GetDevice(wstring_device_id.c_str(), &device); } - device.reset(device_p); - if (FAILED(status)) { + if(FAILED(status)) { BOOST_LOG(error) << "Couldn't create audio Device [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - audio_client_t::pointer audio_client_p{}; status = device->Activate( IID_IAudioClient, CLSCTX_ALL, nullptr, - (void **) &audio_client_p); - audio_client.reset(audio_client_p); + (void **) &audio_client); if (FAILED(status)) { BOOST_LOG(error) << "Couldn't activate audio Device [0x"sv << util::hex(status).to_string_view() << ']'; @@ -132,11 +125,8 @@ public: return -1; } - wave_format_t::pointer wave_format_p{}; - status = audio_client->GetMixFormat(&wave_format_p); - wave_format.reset(wave_format_p); - - if (FAILED(status)) { + status = audio_client->GetMixFormat(&wave_format); + if(FAILED(status)) { BOOST_LOG(error) << "Couldn't acquire Wave Format [0x"sv << util::hex(status).to_string_view() << ']'; return -1; @@ -198,9 +188,7 @@ public: sample_buf = util::buffer_t { frames }; sample_buf_pos = std::begin(sample_buf); - audio_capture_t::pointer audio_capture_p {}; - status = audio_client->GetService(IID_IAudioCaptureClient, (void**)&audio_capture_p); - audio_capture.reset(audio_capture_p); + status = audio_client->GetService(IID_IAudioCaptureClient, (void**)&audio_capture); if (FAILED(status)) { BOOST_LOG(error) << "Couldn't initialize audio capture client [0x"sv << util::hex(status).to_string_view() << ']'; diff --git a/sunshine/platform/windows/display_base.cpp b/sunshine/platform/windows/display_base.cpp index 29b53523..8644ed88 100644 --- a/sunshine/platform/windows/display_base.cpp +++ b/sunshine/platform/windows/display_base.cpp @@ -90,17 +90,10 @@ int display_base_t::init() { FreeLibrary(user32); }); */ - - dxgi::factory1_t::pointer factory_p {}; - dxgi::adapter_t::pointer adapter_p {}; - dxgi::output_t::pointer output_p {}; - dxgi::device_t::pointer device_p {}; - dxgi::device_ctx_t::pointer device_ctx_p {}; HRESULT status; - status = CreateDXGIFactory1(IID_IDXGIFactory1, (void**)&factory_p); - factory.reset(factory_p); + status = CreateDXGIFactory1(IID_IDXGIFactory1, (void**)&factory); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create DXGIFactory1 [0x"sv << util::hex(status).to_string_view() << ']'; return -1; @@ -111,7 +104,8 @@ int display_base_t::init() { auto adapter_name = converter.from_bytes(config::video.adapter_name); auto output_name = converter.from_bytes(config::video.output_name); - for(int x = 0; factory_p->EnumAdapters1(x, &adapter_p) != DXGI_ERROR_NOT_FOUND; ++x) { + adapter_t::pointer adapter_p; + for(int x = 0; factory->EnumAdapters1(x, &adapter_p) != DXGI_ERROR_NOT_FOUND; ++x) { dxgi::adapter_t adapter_tmp { adapter_p }; DXGI_ADAPTER_DESC1 adapter_desc; @@ -121,8 +115,9 @@ int display_base_t::init() { continue; } + dxgi::output_t::pointer output_p; for(int y = 0; adapter_tmp->EnumOutputs(y, &output_p) != DXGI_ERROR_NOT_FOUND; ++y) { - dxgi::output_t output_tmp {output_p }; + dxgi::output_t output_tmp { output_p }; DXGI_OUTPUT_DESC desc; output_tmp->GetDesc(&desc); @@ -173,14 +168,12 @@ int display_base_t::init() { D3D11_CREATE_DEVICE_VIDEO_SUPPORT, featureLevels, sizeof(featureLevels) / sizeof(D3D_FEATURE_LEVEL), D3D11_SDK_VERSION, - &device_p, + &device, &feature_level, - &device_ctx_p); + &device_ctx); adapter_p->Release(); - device.reset(device_p); - device_ctx.reset(device_ctx_p); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create D3D11 device [0x"sv << util::hex(status).to_string_view() << ']'; @@ -216,7 +209,7 @@ int display_base_t::init() { tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; if (!AdjustTokenPrivileges(token, false, &tp, sizeof(tp), NULL, NULL)) { - BOOST_LOG(error) << "Could not set privilege to increase GPU priority"; + BOOST_LOG(warning) << "Could not set privilege to increase GPU priority"; } } @@ -229,17 +222,15 @@ int display_base_t::init() { if (fn) { status = fn(GetCurrentProcess(), D3DKMT_SCHEDULINGPRIORITYCLASS_REALTIME); if (FAILED(status)) { - BOOST_LOG(error) << "Failed to set realtime GPU priority. Please run application as administrator for optimal performance."; + BOOST_LOG(warning) << "Failed to set realtime GPU priority. Please run application as administrator for optimal performance."; } } } - dxgi::dxgi_t::pointer dxgi_p {}; - status = device->QueryInterface(IID_IDXGIDevice, (void**)&dxgi_p); - dxgi::dxgi_t dxgi { dxgi_p }; - + dxgi::dxgi_t dxgi; + status = device->QueryInterface(IID_IDXGIDevice, (void**)&dxgi); if(FAILED(status)) { - BOOST_LOG(error) << "Failed to query DXGI interface from device [0x"sv << util::hex(status).to_string_view() << ']'; + BOOST_LOG(warning) << "Failed to query DXGI interface from device [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } @@ -248,25 +239,24 @@ int display_base_t::init() { // Try to reduce latency { - dxgi::dxgi1_t::pointer dxgi_p {}; - status = device->QueryInterface(IID_IDXGIDevice, (void**)&dxgi_p); - dxgi::dxgi1_t dxgi { dxgi_p }; - + dxgi::dxgi1_t dxgi {}; + status = device->QueryInterface(IID_IDXGIDevice, (void**)&dxgi); if(FAILED(status)) { BOOST_LOG(error) << "Failed to query DXGI interface from device [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - dxgi->SetMaximumFrameLatency(1); + status = dxgi->SetMaximumFrameLatency(1); + if(FAILED(status)) { + BOOST_LOG(warning) << "Failed to set maximum frame latency [0x"sv << util::hex(status).to_string_view() << ']'; + } } //FIXME: Duplicate output on RX580 in combination with DOOM (2016) --> BSOD //TODO: Use IDXGIOutput5 for improved performance { - dxgi::output1_t::pointer output1_p {}; - status = output->QueryInterface(IID_IDXGIOutput1, (void**)&output1_p); - dxgi::output1_t output1 {output1_p }; - + dxgi::output1_t output1 {}; + status = output->QueryInterface(IID_IDXGIOutput1, (void**)&output1); if(FAILED(status)) { BOOST_LOG(error) << "Failed to query IDXGIOutput1 from the output"sv; return -1; @@ -274,10 +264,8 @@ int display_base_t::init() { // We try this twice, in case we still get an error on reinitialization for(int x = 0; x < 2; ++x) { - dxgi::dup_t::pointer dup_p {}; - status = output1->DuplicateOutput((IUnknown*)device.get(), &dup_p); + status = output1->DuplicateOutput((IUnknown*)device.get(), &dup.dup); if(SUCCEEDED(status)) { - dup.reset(dup_p); break; } std::this_thread::sleep_for(200ms); diff --git a/sunshine/platform/windows/display_ram.cpp b/sunshine/platform/windows/display_ram.cpp index 15d608fe..ffcbbd25 100644 --- a/sunshine/platform/windows/display_ram.cpp +++ b/sunshine/platform/windows/display_ram.cpp @@ -203,9 +203,8 @@ capture_e display_ram_t::snapshot(::platf::img_t *img_base, std::chrono::millise // If frame has been updated if (frame_info.LastPresentTime.QuadPart != 0) { { - texture2d_t::pointer src_p {}; - status = res->QueryInterface(IID_ID3D11Texture2D, (void **)&src_p); - texture2d_t src{src_p}; + texture2d_t src {}; + status = res->QueryInterface(IID_ID3D11Texture2D, (void **)&src); if (FAILED(status)) { BOOST_LOG(error) << "Couldn't query interface [0x"sv << util::hex(status).to_string_view() << ']'; @@ -279,10 +278,7 @@ int display_ram_t::init() { t.Format = format; t.CPUAccessFlags = D3D11_CPU_ACCESS_READ; - dxgi::texture2d_t::pointer tex_p {}; - auto status = device->CreateTexture2D(&t, nullptr, &tex_p); - - texture.reset(tex_p); + auto status = device->CreateTexture2D(&t, nullptr, &texture); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create texture [0x"sv << util::hex(status).to_string_view() << ']'; diff --git a/sunshine/platform/windows/display_vram.cpp b/sunshine/platform/windows/display_vram.cpp index c8744b18..00e0c69d 100644 --- a/sunshine/platform/windows/display_vram.cpp +++ b/sunshine/platform/windows/display_vram.cpp @@ -106,14 +106,14 @@ blend_t make_blend(device_t::pointer device, bool enable) { rt.DestBlendAlpha = D3D11_BLEND_ZERO; } - blend_t::pointer blend_p; - auto status = device->CreateBlendState(&bdesc, &blend_p); + blend_t blend; + auto status = device->CreateBlendState(&bdesc, &blend); if(status) { BOOST_LOG(error) << "Failed to create blend state: [0x"sv << util::hex(status).to_string_view() << ']'; return nullptr; } - return blend_t { blend_p }; + return blend; } blob_t convert_UV_vs_hlsl; @@ -280,13 +280,11 @@ public: }; desc.Texture2D.MipLevels = 1; - shader_res_t::pointer cursor_res_p; - auto status = device->CreateShaderResourceView(texture, &desc, &cursor_res_p); + auto status = device->CreateShaderResourceView(texture, &desc, &img.input_res); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create cursor shader resource view [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - img.input_res.reset(cursor_res_p); return 0; } @@ -303,26 +301,19 @@ public: }; desc.Texture2D.MipLevels = 1; - shader_res_t::pointer input_res_p; - auto status = device->CreateShaderResourceView(img.texture.get(), &desc, &input_res_p); + auto status = device->CreateShaderResourceView(img.texture.get(), &desc, &img.input_res); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create input shader resource view [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - img.input_res.reset(input_res_p); } auto input_res_p = img.input_res.get(); - auto cursor_res_p = this->img.input_res.get(); - - auto scene_rt_p = scene_rt.get(); - auto Y_rt_p = nv12_Y_rt.get(); - auto UV_rt_p = nv12_UV_rt.get(); if(cursor_visible) { _init_view_port(img.width, img.height); - device_ctx_p->OMSetRenderTargets(1, &scene_rt_p, nullptr); + device_ctx_p->OMSetRenderTargets(1, &scene_rt, nullptr); device_ctx_p->VSSetShader(scene_vs.get(), nullptr, 0); device_ctx_p->PSSetShader(scene_ps.get(), nullptr, 0); device_ctx_p->PSSetShaderResources(0, 1, &input_res_p); @@ -331,7 +322,7 @@ public: device_ctx_p->OMSetBlendState(blend_enable.get(), nullptr, 0xFFFFFFFFu); device_ctx_p->RSSetViewports(1, &cursor_view); - device_ctx_p->PSSetShaderResources(0, 1, &cursor_res_p); + device_ctx_p->PSSetShaderResources(0, 1, &this->img.input_res); device_ctx_p->Draw(3, 0); device_ctx_p->OMSetBlendState(blend_disable.get(), nullptr, 0xFFFFFFFFu); @@ -339,14 +330,14 @@ public: } _init_view_port(out_width, out_height); - device_ctx_p->OMSetRenderTargets(1, &Y_rt_p, nullptr); + device_ctx_p->OMSetRenderTargets(1, &nv12_Y_rt, nullptr); device_ctx_p->VSSetShader(scene_vs.get(), nullptr, 0); device_ctx_p->PSSetShader(convert_Y_ps.get(), nullptr, 0); device_ctx_p->PSSetShaderResources(0, 1, &input_res_p); device_ctx_p->Draw(3, 0); _init_view_port(out_width / 2, out_height / 2); - device_ctx_p->OMSetRenderTargets(1, &UV_rt_p, nullptr); + device_ctx_p->OMSetRenderTargets(1, &nv12_UV_rt, nullptr); device_ctx_p->VSSetShader(convert_UV_vs.get(), nullptr, 0); device_ctx_p->PSSetShader(convert_UV_ps.get(), nullptr, 0); device_ctx_p->PSSetShaderResources(0, 1, &input_res_p); @@ -380,8 +371,7 @@ public: return; } - auto buf_p = color_matrix.get(); - device_ctx_p->PSSetConstantBuffers(0, 1, &buf_p); + device_ctx_p->PSSetConstantBuffers(0, 1, &color_matrix); this->color_matrix = std::move(color_matrix); } @@ -406,46 +396,43 @@ public: this->out_width = out_width; this->out_height = out_height; - vs_t::pointer vs_p; - status = device_p->CreateVertexShader(scene_vs_hlsl->GetBufferPointer(), scene_vs_hlsl->GetBufferSize(), nullptr, &vs_p); + status = device_p->CreateVertexShader(scene_vs_hlsl->GetBufferPointer(), scene_vs_hlsl->GetBufferSize(), nullptr, &scene_vs); if(status) { - BOOST_LOG(error) << "Failed to create mergeY vertex shader [0x"sv << util::hex(status).to_string_view() << ']'; + BOOST_LOG(error) << "Failed to create scene vertex shader [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - scene_vs.reset(vs_p); - ps_t::pointer ps_p; - status = device_p->CreatePixelShader(convert_Y_ps_hlsl->GetBufferPointer(), convert_Y_ps_hlsl->GetBufferSize(), nullptr, &ps_p); + status = device_p->CreatePixelShader(convert_Y_ps_hlsl->GetBufferPointer(), convert_Y_ps_hlsl->GetBufferSize(), nullptr, &convert_Y_ps); if(status) { - BOOST_LOG(error) << "Failed to create mergeY pixel shader [0x"sv << util::hex(status).to_string_view() << ']'; + BOOST_LOG(error) << "Failed to create convertY pixel shader [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - convert_Y_ps.reset(ps_p); - status = device_p->CreatePixelShader(convert_UV_ps_hlsl->GetBufferPointer(), convert_UV_ps_hlsl->GetBufferSize(), nullptr, &ps_p); + status = device_p->CreatePixelShader(convert_UV_ps_hlsl->GetBufferPointer(), convert_UV_ps_hlsl->GetBufferSize(), nullptr, &convert_UV_ps); if(status) { - BOOST_LOG(error) << "Failed to create mergeUV pixel shader [0x"sv << util::hex(status).to_string_view() << ']'; + BOOST_LOG(error) << "Failed to create convertUV pixel shader [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - convert_UV_ps.reset(ps_p); - status = device_p->CreateVertexShader(convert_UV_vs_hlsl->GetBufferPointer(), convert_UV_vs_hlsl->GetBufferSize(), nullptr, &vs_p); + status = device_p->CreateVertexShader(convert_UV_vs_hlsl->GetBufferPointer(), convert_UV_vs_hlsl->GetBufferSize(), nullptr, &convert_UV_vs); if(status) { - BOOST_LOG(error) << "Failed to create mergeUV vertex shader [0x"sv << util::hex(status).to_string_view() << ']'; + BOOST_LOG(error) << "Failed to create convertUV vertex shader [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - convert_UV_vs.reset(vs_p); - status = device_p->CreatePixelShader(scene_ps_hlsl->GetBufferPointer(), scene_ps_hlsl->GetBufferSize(), nullptr, &ps_p); + status = device_p->CreatePixelShader(scene_ps_hlsl->GetBufferPointer(), scene_ps_hlsl->GetBufferSize(), nullptr, &scene_ps); if(status) { BOOST_LOG(error) << "Failed to create scene pixel shader [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - scene_ps.reset(ps_p); blend_disable = make_blend(device_p, false); blend_enable = make_blend(device_p, true); + if(!blend_disable || !blend_enable) { + return -1; + } + if(_init_rt(scene_sr, scene_rt, in_width, in_height, DXGI_FORMAT_B8G8R8A8_UNORM)) { return -1; } @@ -467,12 +454,10 @@ public: "SV_Position", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }; - input_layout_t::pointer input_layout_p; status = device_p->CreateInputLayout( &layout_desc, 1, convert_UV_vs_hlsl->GetBufferPointer(), convert_UV_vs_hlsl->GetBufferSize(), - &input_layout_p); - input_layout.reset(input_layout_p); + &input_layout); D3D11_TEXTURE2D_DESC t {}; t.Width = out_width; @@ -484,18 +469,16 @@ public: t.Format = pix_fmt == pix_fmt_e::nv12 ? DXGI_FORMAT_NV12 : DXGI_FORMAT_P010; t.BindFlags = D3D11_BIND_RENDER_TARGET; - dxgi::texture2d_t::pointer tex_p {}; - status = device_p->CreateTexture2D(&t, nullptr, &tex_p); + status = device_p->CreateTexture2D(&t, nullptr, &img.texture); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create render target texture [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - img.texture.reset(tex_p); img.display = std::move(display); img.width = out_width; img.height = out_height; - img.data = (std::uint8_t*)tex_p; + img.data = (std::uint8_t*)img.texture.get(); img.row_pitch = out_width; img.pixel_pitch = 1; @@ -504,21 +487,18 @@ public: D3D11_RTV_DIMENSION_TEXTURE2D }; - render_target_t::pointer nv12_rt_p; - status = device_p->CreateRenderTargetView(img.texture.get(), &nv12_rt_desc, &nv12_rt_p); + status = device_p->CreateRenderTargetView(img.texture.get(), &nv12_rt_desc, &nv12_Y_rt); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create render target view [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - nv12_Y_rt.reset(nv12_rt_p); nv12_rt_desc.Format = DXGI_FORMAT_R8G8_UNORM; - status = device_p->CreateRenderTargetView(img.texture.get(), &nv12_rt_desc, &nv12_rt_p); + status = device_p->CreateRenderTargetView(img.texture.get(), &nv12_rt_desc, &nv12_UV_rt); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create render target view [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - nv12_UV_rt.reset(nv12_rt_p); D3D11_SAMPLER_DESC sampler_desc {}; sampler_desc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR; @@ -529,21 +509,16 @@ public: sampler_desc.MinLOD = 0; sampler_desc.MaxLOD = D3D11_FLOAT32_MAX; - sampler_state_t::pointer sampler_state_p; - status = device_p->CreateSamplerState(&sampler_desc, &sampler_state_p); + status = device_p->CreateSamplerState(&sampler_desc, &sampler_linear); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create point sampler state [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - sampler_linear.reset(sampler_state_p); - auto sampler_linear_p = sampler_linear.get(); - auto color_matrix_buf_p = color_matrix.get(); - auto info_buf_p = info_scene.get(); device_ctx_p->OMSetBlendState(blend_disable.get(), nullptr, 0xFFFFFFFFu); - device_ctx_p->PSSetSamplers(0, 1, &sampler_linear_p); - device_ctx_p->PSSetConstantBuffers(0, 1, &color_matrix_buf_p); - device_ctx_p->VSSetConstantBuffers(0, 1, &info_buf_p); + device_ctx_p->PSSetSamplers(0, 1, &sampler_linear); + device_ctx_p->PSSetConstantBuffers(0, 1, &color_matrix); + device_ctx_p->VSSetConstantBuffers(0, 1, &info_scene); device_ctx_p->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP); device_ctx_p->IASetInputLayout(input_layout.get()); @@ -589,13 +564,12 @@ private: auto device = (device_t::pointer)data; - texture2d_t::pointer tex_p; - auto status = device->CreateTexture2D(&desc, nullptr, &tex_p); + texture2d_t tex; + auto status = device->CreateTexture2D(&desc, nullptr, &tex); if(status) { BOOST_LOG(error) << "Failed to create render target texture for luma [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - texture2d_t tex { tex_p }; D3D11_SHADER_RESOURCE_VIEW_DESC shader_resource_desc { @@ -604,26 +578,22 @@ private: }; shader_resource_desc.Texture2D.MipLevels = 1; - shader_res_t::pointer shader_res_p; - device->CreateShaderResourceView(tex_p, &shader_resource_desc, &shader_res_p); + device->CreateShaderResourceView(tex.get(), &shader_resource_desc, &shader_res); if(status) { BOOST_LOG(error) << "Failed to create render target texture for luma [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - shader_res.reset(shader_res_p); D3D11_RENDER_TARGET_VIEW_DESC render_target_desc { format, D3D11_RTV_DIMENSION_TEXTURE2D }; - render_target_t::pointer render_target_p; - device->CreateRenderTargetView(tex_p, &render_target_desc, &render_target_p); + device->CreateRenderTargetView(tex.get(), &render_target_desc, &render_target); if(status) { BOOST_LOG(error) << "Failed to create render target view [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - render_target.reset(render_target_p); return 0; } @@ -721,16 +691,15 @@ capture_e display_vram_t::snapshot(platf::img_t *img_base, std::chrono::millisec t.Format = DXGI_FORMAT_B8G8R8A8_UNORM; t.BindFlags = D3D11_BIND_SHADER_RESOURCE; - dxgi::texture2d_t::pointer tex_p {}; - auto status = device->CreateTexture2D(&t, &data, &tex_p); + texture2d_t texture; + auto status = device->CreateTexture2D(&t, &data, &texture); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create mouse texture [0x"sv << util::hex(status).to_string_view() << ']'; return capture_e::error; } - texture2d_t texture { tex_p }; for(auto *hwdevice : hwdevices) { - if(hwdevice->set_cursor_texture(tex_p, t.Width, t.Height)) { + if(hwdevice->set_cursor_texture(texture.get(), t.Width, t.Height)) { return capture_e::error; } } @@ -747,15 +716,14 @@ capture_e display_vram_t::snapshot(platf::img_t *img_base, std::chrono::millisec } if(frame_update_flag) { - texture2d_t::pointer src_p {}; - status = res->QueryInterface(IID_ID3D11Texture2D, (void **)&src_p); + texture2d_t src; + status = res->QueryInterface(IID_ID3D11Texture2D, (void **)&src); if(FAILED(status)) { BOOST_LOG(error) << "Couldn't query interface [0x"sv << util::hex(status).to_string_view() << ']'; return capture_e::error; } - texture2d_t src { src_p }; device_ctx->CopyResource(img->texture.get(), src.get()); } @@ -775,15 +743,13 @@ std::shared_ptr display_vram_t::alloc_img() { t.Format = format; t.BindFlags = D3D11_BIND_SHADER_RESOURCE; - dxgi::texture2d_t::pointer tex_p {}; - auto status = device->CreateTexture2D(&t, nullptr, &tex_p); + auto status = device->CreateTexture2D(&t, nullptr, &img->texture); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create img buf texture [0x"sv << util::hex(status).to_string_view() << ']'; return nullptr; } - img->texture.reset(tex_p); - img->data = (std::uint8_t*)tex_p; + img->data = (std::uint8_t*)img->texture.get(); img->row_pitch = 0; img->pixel_pitch = 4; img->width = 0; @@ -813,15 +779,15 @@ int display_vram_t::dummy_img(platf::img_t *img_base) { t.Format = format; t.BindFlags = D3D11_BIND_SHADER_RESOURCE; - dxgi::texture2d_t::pointer tex_p {}; - auto status = device->CreateTexture2D(&t, &data, &tex_p); + dxgi::texture2d_t tex; + auto status = device->CreateTexture2D(&t, &data, &tex); if(FAILED(status)) { BOOST_LOG(error) << "Failed to create dummy texture [0x"sv << util::hex(status).to_string_view() << ']'; return -1; } - img->texture.reset(tex_p); - img->data = (std::uint8_t*)tex_p; + img->texture = std::move(tex); + img->data = (std::uint8_t*)img->texture.get(); img->height = height; img->width = width; img->pixel_pitch = 4; diff --git a/sunshine/utility.h b/sunshine/utility.h index 0c03c51d..63be108c 100644 --- a/sunshine/utility.h +++ b/sunshine/utility.h @@ -76,37 +76,6 @@ struct __either { template using either_t = typename __either::type; -template -struct __false_v; - -template -struct __false_v>> { - static constexpr std::nullopt_t value = std::nullopt; -}; - -template -struct __false_v || instantiation_of_v || instantiation_of_v) - >> { - static constexpr std::nullptr_t value = nullptr; -}; - -template -struct __false_v>> { - static constexpr bool value = false; -}; - -template -static constexpr auto false_v = __false_v::value; - -template -using optional_t = either_t< - (std::is_same_v || - instantiation_of_v || - instantiation_of_v || - std::is_pointer_v), - T, std::optional>; - template struct overloaded : Ts... { using Ts::operator()...; }; template overloaded(Ts...) -> overloaded; @@ -362,35 +331,6 @@ auto enm(T& val) -> std::underlying_type_t& { return *reinterpret_cast*>(&val); } -template -struct Function { - typedef ReturnType (*type)(Args...); -}; - -template::type function> -struct Destroy { - typedef T pointer; - - void operator()(pointer p) { - function(p); - } -}; - -template::type function> -using safe_ptr = std::unique_ptr>; - -// You cannot specialize an alias -template::type function> -using safe_ptr_v2 = std::unique_ptr>; - -template -void c_free(T *p) { - free(p); -} - -template -using c_ptr = safe_ptr>; - inline std::int64_t from_chars(const char *begin, const char *end) { std::int64_t res {}; std::int64_t mul = 1; @@ -436,6 +376,163 @@ public: } }; +// Compared to std::unique_ptr, it adds the ability to get the address of the pointer itself +template > +class uniq_ptr { +public: + using element_type = T; + using pointer = element_type*; + using deleter_type = D; + + constexpr uniq_ptr() noexcept : _p { nullptr } {} + constexpr uniq_ptr(std::nullptr_t) noexcept : _p { nullptr } {} + + uniq_ptr(const uniq_ptr &other) noexcept = delete; + uniq_ptr &operator=(const uniq_ptr &other) noexcept = delete; + + template + uniq_ptr(V *p) noexcept : _p { p } { + static_assert(std::is_same_v || std::is_same_v || std::is_base_of_v, "element_type must be base class of V"); + } + + template + uniq_ptr(std::unique_ptr &&uniq) noexcept : _p { uniq.release() } { + static_assert(std::is_same_v || std::is_same_v || std::is_base_of_v, "element_type must be base class of V"); + } + + template + uniq_ptr(uniq_ptr &&other) noexcept : _p { other.release() } { + static_assert(std::is_same_v || std::is_same_v || std::is_base_of_v, "element_type must be base class of V"); + } + + template + uniq_ptr &operator=(uniq_ptr &&other) noexcept { + static_assert(std::is_same_v || std::is_same_v || std::is_base_of_v, "element_type must be base class of V"); + reset(other.release()); + + return *this; + } + + template + uniq_ptr &operator=(std::unique_ptr &&uniq) noexcept { + static_assert(std::is_same_v || std::is_same_v || std::is_base_of_v, "element_type must be base class of V"); + + reset(uniq.release()); + + return *this; + } + + ~uniq_ptr() { + reset(); + } + + void reset(pointer p = pointer()) { + if(_p) { + _deleter(_p); + } + + _p = p; + } + + pointer release() { + auto tmp = _p; + _p = nullptr; + return tmp; + } + + pointer get() { + return _p; + } + + const pointer get() const { + return _p; + } + + const std::add_lvalue_reference_t operator*() const { + return *_p; + } + std::add_lvalue_reference_t operator*() { + return *_p; + } + const pointer operator->() const { + return _p; + } + pointer operator->() { + return _p; + } + pointer *operator&() const { + return &_p; + } + + pointer *operator&() { + return &_p; + } + + deleter_type& get_deleter() { + return _deleter; + } + + const deleter_type& get_deleter() const { + return _deleter; + } + + explicit operator bool() const { + return _p != nullptr; + } +protected: + pointer _p; + deleter_type _deleter; +}; + +template +bool operator==(const uniq_ptr& x, const uniq_ptr& y) { + return x.get() == y.get(); +} + +template +bool operator!=(const uniq_ptr& x, const uniq_ptr& y) { + return x.get() != y.get(); +} + +template +bool operator==(const std::unique_ptr& x, const uniq_ptr& y) { + return x.get() == y.get(); +} + +template +bool operator!=(const std::unique_ptr& x, const uniq_ptr& y) { + return x.get() != y.get(); +} + +template +bool operator==(const uniq_ptr& x, const std::unique_ptr& y) { + return x.get() == y.get(); +} + +template +bool operator!=(const uniq_ptr& x, const std::unique_ptr& y) { + return x.get() != y.get(); +} + +template +bool operator==(const uniq_ptr& x, std::nullptr_t) { + return !(bool)x; +} + +template +bool operator!=(const uniq_ptr& x, std::nullptr_t) { + return (bool)x; +} + +template +bool operator==(std::nullptr_t, const uniq_ptr& y) { + return !(bool)y; +} + +template +bool operator!=(std::nullptr_t, const uniq_ptr& y) { + return (bool)y; +} template class wrap_ptr { @@ -510,6 +607,43 @@ private: pointer _p; }; +template +struct __false_v; + +template +struct __false_v>> { + static constexpr std::nullopt_t value = std::nullopt; +}; + +template +struct __false_v || + instantiation_of_v || + instantiation_of_v || + instantiation_of_v + ) + >> { + static constexpr std::nullptr_t value = nullptr; +}; + +template +struct __false_v>> { + static constexpr bool value = false; +}; + +template +static constexpr auto false_v = __false_v::value; + +template +using optional_t = either_t< + (std::is_same_v || + instantiation_of_v || + instantiation_of_v || + instantiation_of_v || + std::is_pointer_v), + T, std::optional>; + template class buffer_t { public: @@ -569,6 +703,35 @@ T either(std::optional &&l, T &&r) { return std::forward(r); } +template +struct Function { + typedef ReturnType (*type)(Args...); +}; + +template::type function> +struct Destroy { + typedef T pointer; + + void operator()(pointer p) { + function(p); + } +}; + +template::type function> +using safe_ptr = uniq_ptr>; + +// You cannot specialize an alias +template::type function> +using safe_ptr_v2 = uniq_ptr>; + +template +void c_free(T *p) { + free(p); +} + +template +using c_ptr = safe_ptr>; + namespace endian { template struct endianness {