Beispiel #1
0
void XFBEncoder::DecodeToTexture(D3DTexture2D* dst_texture, const u8* src, u32 src_width, u32 src_height)
{
	_assert_msg_(VIDEO, src_width <= MAX_XFB_WIDTH && src_height <= MAX_XFB_HEIGHT, "XFB source does not exceed maximum size");

	// Copy to XFB upload buffer. Each row has to be done separately due to pitch differences.
	u32 buffer_pitch = ROUND_UP(src_width / 2 * sizeof(u32), D3D12_TEXTURE_DATA_PITCH_ALIGNMENT);
	m_upload_buffer->AllocateSpaceInBuffer(buffer_pitch * src_height, D3D12_TEXTURE_DATA_PLACEMENT_ALIGNMENT);
	for (u32 row = 0; row < src_height; row++)
	{
		const u8* row_src = src + (src_width * 2) * row;
		u8* row_dst = reinterpret_cast<u8*>(m_upload_buffer->GetCPUAddressOfCurrentAllocation()) + buffer_pitch * row;
		memcpy(row_dst, row_src, src_width * 2);
	}

	// Copy from upload buffer to intermediate YUYV texture.
	D3D12_PLACED_SUBRESOURCE_FOOTPRINT src_footprint = { m_upload_buffer->GetOffsetOfCurrentAllocation(),{ DXGI_FORMAT_R8G8B8A8_UNORM, src_width / 2, src_height, 1, buffer_pitch } };
	CD3DX12_TEXTURE_COPY_LOCATION src_location(m_upload_buffer->GetBuffer(), src_footprint);
	CD3DX12_TEXTURE_COPY_LOCATION dst_location(m_yuyv_texture->GetTex(), 0);
	CD3DX12_BOX src_box(0, 0, src_width / 2, src_height);
	m_yuyv_texture->TransitionToResourceState(D3D::current_command_list, D3D12_RESOURCE_STATE_COPY_DEST);
	D3D::current_command_list->CopyTextureRegion(&dst_location, 0, 0, 0, &src_location, &src_box);

	// Convert YUYV texture to RGBA texture with pixel shader.
	CD3DX12_RECT src_texture_rect(0, 0, src_width / 2, src_height);
	dst_texture->TransitionToResourceState(D3D::current_command_list, D3D12_RESOURCE_STATE_RENDER_TARGET);
	D3D::current_command_list->OMSetRenderTargets(1, &dst_texture->GetRTV(), FALSE, nullptr);
	D3D::SetViewportAndScissor(0, 0, src_width, src_height);
	D3D::DrawShadedTexQuad(
		m_yuyv_texture, &src_texture_rect, XFB_TEXTURE_WIDTH, XFB_TEXTURE_HEIGHT,
		StaticShaderCache::GetXFBDecodePixelShader(), StaticShaderCache::GetSimpleVertexShader(), StaticShaderCache::GetSimpleVertexShaderInputLayout(),
		{}, 0, DXGI_FORMAT_R8G8B8A8_UNORM, false, false);

	// XFB source textures are expected to be in shader resource state.
	dst_texture->TransitionToResourceState(D3D::current_command_list, D3D12_RESOURCE_STATE_PIXEL_SHADER_RESOURCE);
}
Beispiel #2
0
  void dir_cpi_impl::sync_remove (saga::impl::void_t & ret, 
                                  saga::url            url, 
                                  int                  flags)
  {
     instance_data idata (this);
     saga::url dir_url(idata->location_);
     boost::filesystem::path src_location (idata->location_.get_path(), boost::filesystem::native);
     // complete paths
     boost::filesystem::path src_path (url.get_path(), boost::filesystem::native);
     if ( ! src_path.has_root_path () )
         src_location /= src_path;
     else
         src_location = src_path;

     bool is_src_dir = false;
     if(hdfsExists(fs_, src_location.string().c_str()) != 0)
     {
         SAGA_ADAPTOR_THROW("directory::remove: Can't remove directory: "
           "Does not exist", saga::DoesNotExist);
     }
     else
     {
        hdfsFileInfo *info;
        info = hdfsGetPathInfo(fs_, src_location.string().c_str());
        if(info == NULL)
        {
           SAGA_ADAPTOR_THROW("file_cpi_impl::init failed",
                            saga::NoSuccess);
        }
        if(info->mKind == kObjectKindDirectory)
           is_src_dir = true;
        else
           is_src_dir = false;
        hdfsFreeFileInfo(info, 1);

     }
     if (is_src_dir) {
         if (saga::name_space::Recursive != flags)
         {
             SAGA_ADAPTOR_THROW("directory::remove: Can't remove directory. "
                 "Please use recursive mode!", saga::BadParameter);
         }
         else {
            saga_hdfs_delete(fs_, src_location.string().c_str()); 
         }
     }
     else {
        saga_hdfs_delete(fs_, src_location.string().c_str()); 
     }
  }
Beispiel #3
0
  void dir_cpi_impl::sync_make_dir (saga::impl::void_t & ret, 
                                    saga::url            url, 
                                    int                  flags)
  {
     instance_data idata (this);
    
     // verify current working directory is local
     saga::url dir_url(idata->location_);
    
     boost::filesystem::path src_location (idata->location_.get_path(), boost::filesystem::native);
     // complete paths
     boost::filesystem::path src_path (url.get_path(), boost::filesystem::native);
    
     if ( ! src_path.has_root_path () )
         src_location /= src_path;
     else
         src_location = src_path;

     if(hdfsCreateDirectory(fs_, src_location.string().c_str()) != 0)
     {
        SAGA_ADAPTOR_THROW("Could not create directory", saga::NoSuccess);
     }
  }
Beispiel #4
0
void XFBEncoder::EncodeTextureToRam(u8* dst, u32 dst_pitch, u32 dst_height,
	D3DTexture2D* src_texture, const TargetRectangle& src_rect,
	u32 src_width, u32 src_height, float gamma)
{
	// src_rect is in native coordinates
	// dst_pitch is in words
	u32 dst_width = dst_pitch / 2;
	u32 dst_texture_width = dst_width / 2;
	_assert_msg_(VIDEO, dst_width <= MAX_XFB_WIDTH && dst_height <= MAX_XFB_HEIGHT, "XFB destination does not exceed maximum size");

	// Encode parameters constant buffer used by shader
	struct EncodeParameters
	{
		float src_rect[4];
		float texel_size[4];
	};
	EncodeParameters parameters =
	{
		{
			static_cast<float>(src_rect.left) / static_cast<float>(src_width),
			static_cast<float>(src_rect.top) / static_cast<float>(src_height),
		static_cast<float>(src_rect.right) / static_cast<float>(src_width),
		static_cast<float>(src_rect.bottom) / static_cast<float>(src_height)
		},
		{
			1.0f / static_cast<float>(src_width),
			1.0f / static_cast<float>(src_height),
		0.0f,
		0.0f
		}
	};
	m_encode_params_buffer->AllocateSpaceInBuffer(sizeof(parameters), D3D12_CONSTANT_BUFFER_DATA_PLACEMENT_ALIGNMENT);
	memcpy(m_encode_params_buffer->GetCPUAddressOfCurrentAllocation(), &parameters, sizeof(parameters));

	// Convert RGBA texture to YUYV intermediate texture.
	// Performs downscaling through a linear filter. Probably not ideal, but it's not going to look perfect anyway.
	CD3DX12_RECT src_texture_rect(src_rect.left, src_rect.top, src_rect.right, src_rect.bottom);
	m_yuyv_texture->TransitionToResourceState(D3D::current_command_list, D3D12_RESOURCE_STATE_RENDER_TARGET);
	D3D::current_command_list->OMSetRenderTargets(1, &m_yuyv_texture->GetRTV(), FALSE, nullptr);
	D3D::current_command_list->SetGraphicsRootConstantBufferView(DESCRIPTOR_TABLE_PS_CBVONE, m_encode_params_buffer->GetGPUAddressOfCurrentAllocation());
	D3D::command_list_mgr->SetCommandListDirtyState(COMMAND_LIST_STATE_PS_CBV, true);
	D3D::SetViewportAndScissor(0, 0, dst_texture_width, dst_height);
	D3D::SetLinearCopySampler();
	D3D::DrawShadedTexQuad(
		src_texture, &src_texture_rect, src_rect.GetWidth(), src_rect.GetHeight(),
		StaticShaderCache::GetXFBEncodePixelShader(), StaticShaderCache::GetSimpleVertexShader(), StaticShaderCache::GetSimpleVertexShaderInputLayout(),
		{}, 0, DXGI_FORMAT_R8G8B8A8_UNORM, false, false);

	// Copy from YUYV intermediate texture to readback buffer. It's likely the pitch here is going to be different to dst_pitch.
	u32 readback_pitch = ROUND_UP(dst_width * sizeof(u16), D3D12_TEXTURE_DATA_PITCH_ALIGNMENT);
	D3D12_PLACED_SUBRESOURCE_FOOTPRINT dst_footprint = { 0,{ DXGI_FORMAT_R8G8B8A8_UNORM, dst_texture_width, dst_height, 1, readback_pitch } };
	CD3DX12_TEXTURE_COPY_LOCATION dst_location(m_readback_buffer, dst_footprint);
	CD3DX12_TEXTURE_COPY_LOCATION src_location(m_yuyv_texture->GetTex(), 0);
	CD3DX12_BOX src_box(0, 0, dst_texture_width, dst_height);
	m_yuyv_texture->TransitionToResourceState(D3D::current_command_list, D3D12_RESOURCE_STATE_COPY_SOURCE);
	D3D::current_command_list->CopyTextureRegion(&dst_location, 0, 0, 0, &src_location, &src_box);

	// Wait until the GPU completes the copy. Resets back to known state automatically.
	D3D::command_list_mgr->ExecuteQueuedWork(true);

	// Copy from the readback buffer to dst.
	// Can't be done as one memcpy due to pitch difference.
	void* readback_texture_map;
	D3D12_RANGE read_range = { 0, readback_pitch * dst_height };
	CheckHR(m_readback_buffer->Map(0, &read_range, &readback_texture_map));

	for (u32 row = 0; row < dst_height; row++)
	{
		const u8* row_src = reinterpret_cast<u8*>(readback_texture_map) + readback_pitch * row;
		u8* row_dst = dst + dst_pitch * row;
		memcpy(row_dst, row_src, std::min(dst_pitch, readback_pitch));
	}
	D3D12_RANGE write_range = {};
	m_readback_buffer->Unmap(0, &write_range);
}
Beispiel #5
0
  void dir_cpi_impl::sync_move (saga::impl::void_t & ret, 
                                saga::url            src, 
                                saga::url            dest, 
                                int                  flags)
  {
     instance_data idata (this);
     
     // verify current working directory is local
     saga::url url(idata->location_);
     
     // handle the files
     boost::filesystem::path src_location (idata->location_.get_path(), boost::filesystem::native);
     boost::filesystem::path dst_location (src_location);
     // complete paths
     boost::filesystem::path src_path  (src.get_path(), boost::filesystem::native);
     boost::filesystem::path dest_path (dest.get_path(), boost::filesystem::native);
     
     if ( ! src_path.has_root_path () )
         src_location /= src_path;
     else
         src_location = src_path;
     
     if ( ! dest_path.has_root_path () )
         dst_location /= dest_path;
     else
         dst_location = dest_path;
     
     bool is_src_dir;
     bool is_dst_dir;
     if(hdfsExists(fs_, src_location.string().c_str()) == 0)
     {
        //Check to see if it is a directory
        hdfsFileInfo *info;
       
        info = hdfsGetPathInfo(fs_, src_location.string().c_str());
        if(info == NULL)
        {
           SAGA_ADAPTOR_THROW("file_cpi_impl::init failed",
                            saga::NoSuccess);
        }
        if(info->mKind == kObjectKindDirectory)
           is_src_dir = true;
        else
           is_src_dir = false;
        hdfsFreeFileInfo(info, 1);
     }
     bool dst_exists = false;
     if(hdfsExists(fs_, dst_location.string().c_str()) == 0)
     {
        dst_exists = true;
        //Check to see if it is a directory
        hdfsFileInfo *info;
       
        info = hdfsGetPathInfo(fs_, dst_location.string().c_str());
        if(info == NULL)
        {
           SAGA_ADAPTOR_THROW("file_cpi_impl::init failed",
                            saga::NoSuccess);
        }
        if(info->mKind == kObjectKindDirectory)
           is_dst_dir = true;
        else
           is_dst_dir = false;
        hdfsFreeFileInfo(info, 1);
     }
     
     if (!is_src_dir && is_dst_dir)
         dst_location /= src_location.leaf();
     
     if ((flags & saga::name_space::Overwrite) && dst_exists) {
/*         if (is_dst_dir)
             fs::remove_all(dst_location);*/
        saga_hdfs_delete(fs_, dst_location.string().c_str()); 
     }
     // if destination still exists raise an error
     dst_exists = false;
     if(hdfsExists(fs_, dst_location.string().c_str()) == 0)
     {
        SAGA_OSSTREAM strm;
        strm << "namespace_dir_cpi_impl<Base>::sync_move: "
            "target file already exists: " << dest.get_url();
        SAGA_ADAPTOR_THROW(SAGA_OSSTREAM_GETSTRING(strm), saga::AlreadyExists);
     }
     if(hdfsMove(fs_, src_location.string().c_str(), fs_, dst_location.string().c_str()) != 0)
     {
        SAGA_ADAPTOR_THROW("Unable to move files", saga::NoSuccess);
     }
  }
Beispiel #6
0
  void dir_cpi_impl::sync_copy (saga::impl::void_t & ret, 
                                saga::url            src, 
                                saga::url            dst, 
                                int                  flags)
  {
     instance_data idata (this);
     saga::url url(idata->location_);
   
     // handle the files
     boost::filesystem::path src_location (idata->location_.get_path(), boost::filesystem::native);
     boost::filesystem::path dst_location (src_location);
   
     // complete paths
     boost::filesystem::path src_path  (src.get_path(), boost::filesystem::native);
     boost::filesystem::path dest_path (dst.get_path(), boost::filesystem::native);
   
     if ( ! src_path.has_root_path () )
         src_location /= src_path;
     else
         src_location = src_path;
   
     if ( ! dest_path.has_root_path () )
         dst_location /= dest_path;
     else
         dst_location = dest_path;

     bool is_src_dir = false;
     if(hdfsExists(fs_, src_location.string().c_str()) == 0)
     {
        //Check to see if it is a directory
        hdfsFileInfo *info;

        info = hdfsGetPathInfo(fs_, src_location.string().c_str());
        if(info == NULL)
        {
           SAGA_ADAPTOR_THROW("file_cpi_impl::init failed",
              saga::NoSuccess);
        }
        if(info->mKind == kObjectKindDirectory)
           is_src_dir = true;
        hdfsFreeFileInfo(info, 1);
     }
     // src location refers to a is a directory
     if (is_src_dir) {
        SAGA_ADAPTOR_THROW("Cannot copy directory at moment.", saga::NotImplemented);
     }
     else {
         //Check to see if dst_location is a directory
        bool is_dst_dir = false;
        bool dst_exists = false;
        if(hdfsExists(fs_, dst_location.string().c_str()) == 0)
        {
           dst_exists = true;
           //Check to see if it is a directory
           hdfsFileInfo *info;
          
           info = hdfsGetPathInfo(fs_, dst_location.string().c_str());
           if(info == NULL)
           {
              SAGA_ADAPTOR_THROW("file_cpi_impl::init failed",
                               saga::NoSuccess);
           }
           if(info->mKind == kObjectKindDirectory)
              is_dst_dir = true;
           hdfsFreeFileInfo(info, 1);
        }
        else
        {
           SAGA_ADAPTOR_THROW("Path does not exists!", saga::NoSuccess);
        }

        if (is_dst_dir)
            dst_location /= src_location.leaf();
    
        // remove the file/directory if it exists and we should overwrite
        if ((flags & saga::name_space::Overwrite) && dst_exists) {
/*            if (is_dst_dir)
                fs::remove_all(dst_location);*/
           saga_hdfs_delete(fs_, dst_location.string().c_str()); 
        }
    
        if(hdfsExists(fs_, dst_location.string().c_str()) == 0)
        {
            SAGA_OSSTREAM strm;
            strm << "namespace_dir_cpi_impl<Base>::sync_copy: "
                "target file already exists: " << dst.get_url();
            SAGA_ADAPTOR_THROW(SAGA_OSSTREAM_GETSTRING(strm), saga::AlreadyExists);
        }
        if(hdfsCopy(fs_, src_location.string().c_str(), fs_, dst_location.string().c_str()) != 0)
        {
            SAGA_OSSTREAM strm;
            strm << "namespace_dir_cpi_impl<Base>::sync_copy: "
                "target file did not copy successfully: " << dst.get_url();
            SAGA_ADAPTOR_THROW(SAGA_OSSTREAM_GETSTRING(strm), saga::NoSuccess);
        }
     }
  }