window显示驱动开发—内容保护的资源

以下 D3DDDI_RESOURCEFLAGS 标志由 Direct3D 运行时用于受保护内容。 运行时在D3DDDIARG_CREATERESOURCE结构的Flags 成员中设置这些 D3DDDI_RESOURCEFLAGS标志,当运行时调用 CreateResource 时,驱动程序的 CreateResource 函数的 pResource 参数指向这些标志。

RestrictedContent

资源可能包含受保护的内容。 在应用程序创建资源之前,应用程序可能已显式启用内容保护,也可能未显式启用内容保护。 驱动程序应确保运行时将资源的分配置于可以保护的内存池中。 驱动程序应允许创建可锁定的受保护资源。 但是,在启用内容保护时,驱动程序应显式失败对其 Lock 函数的调用以锁定这些图面。

RestrictSharedAccess

应仅允许特定进程访问共享资源。

驱动程序应限制对此资源的共享访问。 运行时只能调用驱动程序的 OpenResource 函数,以使用创建资源的进程中的显示设备 (hDevice) 打开此资源,或者由那些通过经过身份验证的通道显式授予访问权限的设备打开此资源。

1. 受保护资源标志处理

1.1 CreateResource 中的标志解析

复制代码
HRESULT APIENTRY CreateResource(
    D3DDDIARG_CREATERESOURCE* pResource)
{
    // 检查受保护内容标志
    const BOOL bProtected = pResource->Flags.RestrictedContent;
    const BOOL bRestrictShared = pResource->Flags.RestrictSharedAccess;
    
    // 验证标志组合有效性
    if (bRestrictShared && !bProtected) {
        return E_INVALIDARG; // 仅限制共享必须配合保护内容
    }
    
    // 分配受保护内存
    if (bProtected) {
        return CreateProtectedResource(pResource);
    }
    
    // 普通资源创建流程
    return CreateStandardResource(pResource);
}

2. 受保护资源创建实现

2.1 安全内存分配

复制代码
HRESULT CreateProtectedResource(D3DDDIARG_CREATERESOURCE* pResource)
{
    PROTECTED_RESOURCE_CTX* pCtx = new PROTECTED_RESOURCE_CTX;
    
    // 设置安全内存属性
    D3DKMT_ALLOCATIONPROPERTIES allocProps = {0};
    allocProps.Protected = TRUE;
    allocProps.RestrictSharedAccess = pResource->Flags.RestrictSharedAccess;
    
    // 调用KMD接口
    NTSTATUS status = D3DKMTCreateAllocation(
        &allocProps,
        &pCtx->hAllocation);
    
    if (!NT_SUCCESS(status)) {
        delete pCtx;
        return E_FAIL;
    }
    
    // 标记为可锁定但实际锁定会失败
    pCtx->bLockable = pResource->Flags.Dynamic;
    
    // 存储到资源表
    pResource->hResource = (HANDLE)pCtx;
    return S_OK;
}

3. 资源锁定保护机制

3.1 Lock 函数特殊处理

复制代码
HRESULT APIENTRY Lock(D3DDDIARG_LOCK* pLock)
{
    PROTECTED_RESOURCE_CTX* pCtx = 
        (PROTECTED_RESOURCE_CTX*)pLock->hResource;
    
    // 检查保护状态
    if (IsResourceProtected(pCtx)) {
        // 动态资源在未启用保护时可锁定
        if (pCtx->bLockable && !IsContentProtectionActive()) {
            return StandardLock(pLock);
        }
        return D3DDDIERR_LOCKEDPROTECTEDRESOURCE;
    }
    
    return StandardLock(pLock);
}

保护规则矩阵:

资源类型 RestrictedContent Lock行为
静态纹理 TRUE 始终失败
动态纹理 TRUE 保护激活时失败
任何缓冲区 FALSE 正常锁定

4. 共享访问控制

4.1 OpenResource 访问检查

复制代码
HRESULT APIENTRY OpenResource(
    D3DDDIARG_OPENRESOURCE* pOpenResource)
{
    PROTECTED_RESOURCE_CTX* pOriginal = 
        (PROTECTED_RESOURCE_CTX*)pOpenResource->hResource;
    
    // 检查共享限制
    if (pOriginal->Flags.RestrictSharedAccess) {
        // 验证调用进程权限
        if (!CheckAccessRights(
                pOpenResource->hDevice,
                pOriginal->hAllocation)) {
            return E_ACCESSDENIED;
        }
    }
    
    // 标准打开流程
    return StandardOpenResource(pOpenResource);
}

4.2 访问验证逻辑

复制代码
BOOL CheckAccessRights(
    HANDLE hDevice, 
    D3DKMT_HANDLE hAllocation)
{
    // 1. 检查是否同一进程
    if (IsCreatorProcess(hDevice, hAllocation))
        return TRUE;
    
    // 2. 检查认证通道授权
    if (HasAuthenticatedAccess(hDevice, hAllocation))
        return TRUE;
    
    return FALSE;
}

5. 安全架构设计

5.1 资源元数据结构

复制代码
typedef struct _PROTECTED_RESOURCE_CTX {
    D3DKMT_HANDLE hAllocation;      // 内核分配句柄
    D3DDDI_RESOURCEFLAGS Flags;      // 原始标志
    BOOL bLockable;                  // 动态资源标记
    SECURITY_DESCRIPTOR* pSD;        // 安全描述符(可选)
} PROTECTED_RESOURCE_CTX;

5.2 内存保护实现

6. 错误处理规范

错误码 触发条件
D3DDDIERR_LOCKEDPROTECTEDRESOURCE 尝试锁定受保护资源
E_ACCESSDENIED 非法共享访问尝试
E_INVALIDARG 无效的标志组合

7. 性能优化建议

保护内存池管理:

复制代码
class SecureMemoryPool {
public:
    void* Alloc(size_t size) {
        return VirtualAlloc(NULL, size, 
            MEM_RESERVE | MEM_COMMIT, 
            PAGE_READWRITE | PAGE_GUARD);
    }
};

批量资源创建:

复制代码
void CreateMultipleResources(
    D3DDDIARG_CREATERESOURCE* pResources, 
    UINT count)
{
    if (AllProtected(pResources, count)) {
        HW_BulkCreateSecureResources(pResources);
    }
}

8. 认证测试要求

WHQL测试项目:

  • 保护资源锁定负向测试
  • 跨进程共享测试
  • 标志组合有效性测试

安全测试用例:

复制代码
# 伪代码:尝试突破共享限制
def test_shared_violation():
    hRes = create_protected_resource()
    try:
        open_from_other_process(hRes)
        assert False # 应抛出访问拒绝
    except AccessDeniedError:
        pass

9. 向后兼容性

复制代码
#if (D3D_UMD_INTERFACE_VERSION >= D3D_UMD_INTERFACE_VERSION_WIN7)
    // 完整实现保护标志
#else
    // 忽略保护标志,仅记录警告
    if (pResource->Flags.RestrictedContent)
        DebugPrint("保护内容需要Win7+驱动模型");
#endif
相关推荐
nuoxin11414 小时前
GSV1011-富利威-HDMI芯片选型
arm开发·驱动开发·fpga开发·ffmpeg·射频工程
快乐的学习21 小时前
开源相关术语及提交commit关键字总结
驱动开发·开源
hhwyqwqhhwy1 天前
linux 驱动开发相关
linux·驱动开发
偶像你挑的噻2 天前
11-Linux驱动开发-I2C子系统–mpu6050简单数据透传驱动
linux·驱动开发·stm32·嵌入式硬件
UVM_ERROR2 天前
硬件设计实战:解决Valid单拍采样失效问题(附非阻塞赋值与时序对齐核心要点)
驱动开发·fpga开发·github·芯片
python百炼成钢3 天前
28.嵌入式 Linux LED 驱动开发实验
linux·运维·驱动开发
LUCIFER3 天前
驱动开发:详细分析 DTB、DTS、DTSI、DTBO 的区别、用途及它们之间的关系
linux·服务器·驱动开发
偶像你挑的噻4 天前
9-Linux驱动开发-设备树=>设备树插件实现 RGB 灯驱动
linux·驱动开发·stm32·嵌入式硬件
沟通QQ:276998854 天前
虚拟同步机控制结构图](https://app.sxlcdn.com/upfile/2264/phi_153621_20_lyxqk2vj.png
驱动开发
DeeplyMind5 天前
Linux Virtio 子系统核心数据结构解析
linux·驱动开发·virtio-gpu