ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

WSL WslcSetContainerSettingsNamedVolumes 详解:为 WSL 容器配置命名卷挂载

WSL WslcSetContainerSettingsNamedVolumes 详解:为 WSL 容器配置命名卷挂载 WSL WslcSetContainerSettingsNamedVolumes 详解为 WSL 容器配置命名卷挂载【免费下载链接】WSLWindows Subsystem for Linux项目地址: https://gitcode.com/GitHub_Trending/ws/WSL本篇技术指南聚焦 WSLWindows Subsystem for Linux开源仓库中 WslcSDK 提供的容器管理 APIWslcSetContainerSettingsNamedVolumes。该函数用于在创建 WSL 容器之前为WslcContainerSettings配置一组命名卷named volume及其在容器内的挂载路径。读完本文你将掌握该 API 的函数签名、参数语义、WslcContainerNamedVolume结构体字段、与WslcCreateSessionVhdVolume的配合方式、HRESULT 返回约定以及仓库中对应实现与测试用例的验证路径。函数原型与参数解析WslcSetContainerSettingsNamedVolumes在 SDK 头文件 wslcsdk.h 中声明并在 wslcsdk.cpp 中实现。其 C 接口原型如下STDAPI WslcSetContainerSettingsNamedVolumes( _In_ WslcContainerSettings* containerSettings, _In_reads_opt_(namedVolumeCount) const WslcContainerNamedVolume* namedVolumes, _In_ uint32_t namedVolumeCount);参数类型方向说明containerSettingsWslcContainerSettings*in待修改的容器设置句柄必须先通过WslcInitContainerSettings初始化namedVolumesconst WslcContainerNamedVolume*in, optional命名卷描述结构体数组可为nullptrnamedVolumeCountuint32_tinnamedVolumes数组的元素个数函数属于OPTIONAL CONTAINER SETTINGS可选容器设置一族头文件注释明确指出它用于将通过WslcCreateSessionVhdVolume创建的会话命名卷named session volumes添加到容器设置中随后由WslcCreateContainer在创建容器时消费这些配置。WslcContainerNamedVolume 结构体详解命名卷的语义由 wslcsdk.h 中的结构体定义承载typedef struct WslcContainerNamedVolume { _In_z_ PCSTR name; // Name of the session volume (from WslcVhdRequirements.name) _In_z_ PCSTR containerPath; // Absolute path inside the container _In_ BOOL readOnly; } WslcContainerNamedVolume;三个字段的核心语义namePCSTR必填会话卷的名称。该名称来源于创建卷时传入的WslcVhdRequirements.name见 wslcsdk.hSDK 通过该名称在会话内定位已创建的 VHD 卷。containerPathPCSTR必填卷在容器内的挂载目标路径必须是绝对路径如/var/cache/demo。readOnlyBOOL是否以只读方式挂载。FALSE表示读写挂载。对比同族的普通卷结构体WslcContainerVolumewslcsdk.h可以发现关键差异普通卷通过windowsPath直接绑定 Windows 宿主目录而命名卷没有 Windows 路径字段——它引用的是由 SDK 在会话中创建的、与容器生命周期解耦的持久化 VHD 卷这正是其命名named含义所在。参数校验与 HRESULT 返回值函数返回HRESULT。从实现 wslcsdk.cpp 可以看到严格的入参校验逻辑STDAPI WslcSetContainerSettingsNamedVolumes( _In_ WslcContainerSettings* containerSettings, _In_reads_opt_(namedVolumeCount) const WslcContainerNamedVolume* namedVolumes, _In_ uint32_t namedVolumeCount) try { auto internalType CheckAndGetInternalType(containerSettings); RETURN_HR_IF(E_INVALIDARG, (namedVolumes nullptr namedVolumeCount ! 0) || (namedVolumes ! nullptr namedVolumeCount 0)); for (uint32_t i 0; i namedVolumeCount; i) { RETURN_HR_IF_NULL(E_INVALIDARG, namedVolumes[i].name); RETURN_HR_IF_NULL(E_INVALIDARG, namedVolumes[i].containerPath); EnsureAbsolutePath(namedVolumes[i].containerPath, true); } internalType-namedVolumes namedVolumes; internalType-namedVolumesCount namedVolumeCount; return S_OK; } CATCH_RETURN();由此可以归纳出可验证的返回约定返回 HRESULT触发条件S_OK校验通过命名卷数组已写入内部设置E_INVALIDARGnamedVolumes与namedVolumeCount不匹配一个为 NULL 而另一个非 0数组中任一name或containerPath为NULLcontainerPath不是绝对路径其他失败 HRESULTcontainerSettings无效或发生未捕获异常由CATCH_RETURN()统一转换实现采用浅拷贝策略仅将外部数组指针保存到内部结构因此调用方必须保证数组在WslcCreateContainer被调用之前保持有效。containerPath通过EnsureAbsolutePath(path, true)校验第二个参数表示 Linux/容器内路径语义确保必须是如/data这样的绝对路径这与仓库中所有容器内路径校验逻辑保持一致。完整实战示例创建会话卷并挂载到容器结合官方文档示例与源码实现下面给出一个自洽的完整流程先在会话中创建命名卷再通过WslcSetContainerSettingsNamedVolumes将其挂载到容器的/var/cache/demo。#include windows.h #include wslcsdk.h HRESULT ConfigureContainerWithNamedVolume(WslcSession session, WslcContainerSettings* containerSettings) { // 1) 在会话中创建一个名为 cache 的动态 VHD 命名卷1 GiB WslcVhdRequirements vhdReq{}; vhdReq.name cache; vhdReq.sizeBytes 1024ULL * 1024 * 1024; // 1 GiB vhdReq.type WSLC_VHD_TYPE_DYNAMIC; // 动态扩展 VHDX默认 vhdReq.flags WSLC_VHD_REQ_FLAG_NONE; PWSTR errorMessage nullptr; HRESULT hr WslcCreateSessionVhdVolume(session, vhdReq, errorMessage); if (FAILED(hr)) { return hr; } // 2) 描述命名卷在容器内的挂载方式 WslcContainerNamedVolume namedVolumes[1] { 0 }; namedVolumes[0].name cache; namedVolumes[0].containerPath /var/cache/demo; namedVolumes[0].readOnly FALSE; // 3) 写入容器设置 hr WslcSetContainerSettingsNamedVolumes( containerSettings, namedVolumes, (uint32_t)_countof(namedVolumes)); if (FAILED(hr)) { return hr; } // 4) 后续即可调用 WslcCreateContainer 创建容器命名卷会以读写方式挂载到 /var/cache/demo return S_OK; }需要说明的要点WslcCreateSessionVhdVolume实现见 wslcsdk.cpp是命名卷的创建入口。它校验name非空、sizeBytes非 0并只接受WSLC_VHD_REQ_FLAG_OWNER一个已知标志位卷的底层驱动为vhd支持动态WSLC_VHD_TYPE_DYNAMIC与固定WSLC_VHD_TYPE_FIXED两种分配类型后者的驱动选项会追加{Fixed, true}。若需要设置卷的属主可设置WSLC_VHD_REQ_FLAG_OWNER并填写uid/gid字段SDK 会将其转换为Uid/Gid驱动选项传给底层卷创建逻辑见 wslcsdk.cpp。卷的生命周期独立于容器删除卷使用WslcDeleteSessionVhdVolumewslcsdk.cpp。这意味着即使容器被移除命名卷中的数据仍然保留可被后续容器重新挂载。WinRT 层封装ContainerNamedVolume对于使用 WinRT/C 的调用方SDK 在 winrt/ContainerNamedVolume.cpp 中提供了ContainerNamedVolume包装类构造函数签名为ContainerNamedVolume(name, containerPath, readOnly)。该包装类值得注意的行为包括构造时对name与containerPath做非空校验为空则抛出hresult_invalid_argument三个属性均提供 getter/setter但一旦ToStruct()被调用即选项已应用到容器设置任何属性再赋值都会抛出hresult_illegal_state_change防止在配置提交后修改卷定义ToStruct()将 WinRT 对象转换为原生WslcContainerNamedVolume结构体供WslcSetContainerSettingsNamedVolumes使用。在 winrt/ContainerSettings.cpp 中可以看到高层封装如何聚合命名卷ContainerSettings遍历其NamedVolumes集合逐项调用GetStruct转换为原生结构体再一次性调用WslcSetContainerSettingsNamedVolumes写入。测试用例与验证路径仓库的 Windows 测试套件 WSLCTests.cpp 中包含针对命名卷功能的系统化测试可作为理解该 API 行为的权威参考NamedVolumesVhd/NamedVolumesGuest约 WSLCTests.cpp分别验证vhd与guest两种卷驱动下的挂载契约——先以读写方式挂载写入数据再以只读方式挂载同一卷验证数据可读、写入被拒绝NamedVolumesVhdOwnership约 WSLCTests.cpp验证WSLC_VHD_REQ_FLAG_OWNER与 uid/gid 属主语义NamedVolumesVhdFixed约 WSLCTests.cpp验证固定分配 VHDX 的行为NamedVolumeRecovery/NamedVolumesVhdSessionRecovery约 WSLCTests.cpp验证会话/容器重启后命名卷数据的持久性恢复ListAndInspectNamedVolumesTest约 WSLCTests.cpp验证命名卷的枚举与 inspect 能力包括通过 driver 与 label 过滤卷。测试中的duplicateNamedVolumes用例WSLCTests.cpp还覆盖了同一命名卷以不同挂载点、不同只读属性挂载到同一容器的边界场景说明一个卷可同时以读写挂载到/data-a、只读挂载到/data-b。使用注意事项小结调用顺序必须先WslcInitContainerSettings初始化容器设置再调用本函数命名卷本身需先通过WslcCreateSessionVhdVolume创建且两者都必须在WslcCreateContainer之前完成。数组生命周期实现采用指针浅拷贝namedVolumes数组在容器创建完成前必须保持有效。路径规则containerPath必须是容器内的绝对路径否则返回E_INVALIDARG。命名卷与普通卷的区别普通卷WslcSetContainerSettingsVolumes绑定 Windows 宿主路径随容器配置挂载命名卷引用会话级持久化 VHD数据独立于容器生命周期适合缓存、数据库数据目录等需要跨容器复用的场景。导出与链接该符号已通过 wslcsdk.def 导出使用方链接wslcsdk库即可获得该 API。通过本文介绍的 API 与配套卷创建接口开发者可以在 WSL 容器场景下实现容器可销毁、数据可持久的命名卷数据管理方案这正是仓库中vhd驱动命名卷所承载的核心能力。【免费下载链接】WSLWindows Subsystem for Linux项目地址: https://gitcode.com/GitHub_Trending/ws/WSL创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表