通过安装系统 SSD 将物理 Ubuntu 20.04 桌面迁移到 Windows 11 中的 WSLg

通过安装系统 SSD 将物理 Ubuntu 20.04 桌面迁移到 Windows 11 中的 WSLg

我有一个现有的物理 Ubuntu 20.04 桌面系统,运行在 SSD 上,以 ext4 作为文件系统。

我将 SSD 安装到 Windows 11 中的 WSLg Ubuntu 中。

为了尽可能保持相同的体验,我想使用挂载的SSD作为主系统磁盘来取代WSLg中Ubuntu的默认安装。

那可能吗?

我尝试在 WSLg 中 chroot 到 SSD 并成功运行了一些 CLI 软件。但它无法启动所有 GUI 应用程序,例如 Jetbrains IDE。

而且,迁移后,我希望在需要时仍然能够使用相同的 SSD 启动相同的物理 Ubuntu 系统。

答案1

虽然我还不确定是否有办法将驱动器本身用作 WSL 实例,但我确实认为我们可以使 chroot 方法发挥作用,至少在某种程度上。

以下是我使用的设置:

  • Ubuntu Base 21.10 rootfs 映像提取(作为 sudo)到$HOME/chroot/Ubuntu21.10
  • 为了进行测试,完成以下配置后,apt install xterm
  • 对于任何尝试使用实际 rootfs 进行此操作的人,请注意您应该使用以下xattrs选项解压,例如:
    # Download Ubuntu Base rootfs into the current directory, then:
    mkdir Ubuntu21.10
    cd !$
    sudo tar -xvz --xattrs -f ../ubuntu-base-21.10-base-amd64.tar.gz
    

我一眼就看出来,这完全可以准确表示您能够挂载到 WSL/Ubuntu 实例内目录中的现有 SSD。但是,我确信您的配置中肯定有一些我没有预料到的项目。如果您遇到问题,请通过此处的评论(如果有必要,也可以通过新问题)告诉我。

哪些措施有效

  • 联网
  • .exe在 chroot 中运行 Windows (包括 GUI 应用程序)
  • 在 chroot 中运行 Linux GUI 应用程序(当然需要 Windows 11)

已知不起作用的方法

  • 无法从 chroot 中挂载 Windows 驱动器(例如mount -t drvfs ...)。这可能是因为我还没有找到挂载特殊 WSLdriverslib文件系统的方法。其他一切都可以通过将mount实际文件系统的 a 放入 chroot 路径或通过将mount --bind现有路径从 WSL 放入 chroot 路径(“绑定挂载”)来工作。

  • Windows 路径未填充到 chroot 的路径中(WSL 通常通过 执行此操作)/init。这意味着您必须使用完全限定路径来运行任何.exes。填充路径对于脚本来说并不困难,但是这个答案已经够长了,所以我将把 作为练习留给读者(或单独的问题)。

未测试

  • 音频:如果它不起作用,那么可能只是找到正确的环境变量的问题,或者可能需要安装一个套接字(如果需要)。

  • VSCode: 可能由于 VSCode 的“默认用户”期望而出现问题)

  • 还有很多其他的东西

一次性准备

首次准备 chroot 文件系统时需要完成一些任务。

  • 从 WSL 内部(而不是在 chroot 中)创建挂载点并复制一些 WSL 项目:

    cd <your_chroot_mountpoint_root>
    # Create mount points
    sudo mkdir mnt/c
    sudo mkdir run/WSL
    sudo mkdir mnt/wslg
    sudo mkdir mnt/wsl
    sudo mkdir -p usr/lib/wsl/drivers usr/lib/wsl/lib
    
    # Copy WSL generated config files - Currently doesn't work, but there for future reference/use
    # sudo cp /etc/ld.so.conf.d/ld.wsl.conf etc/ld.so.conf.d
    
    # Delete existing resolv.conf and use the one generated by WSL
    sudo rm etc/resolv.conf
    sudo ln -rs mnt/wsl/resolv.conf etc/
    
    # Delete existing X socket (if exists) and use the one generated by WSL
    [ -S tmp/.X11-unix ] && sudo rm tmp/.X11-unix
    [ -f tmp/.X11-unix ] && sudo rm tmp/.X11-unix
    [ -L tmp/.X11-unix ] && sudo rm tmp/.X11-unix
    sudo ln -rs mnt/wslg/.X11-unix/ tmp/.X11-unix
    
    # Set up fstab for recurring mount points.
    
    # (0) Make sure you are in the root of the chroot
    #     (the mounted drive, in your case) before
    #     running each command.
    # (A) I suggest running these lines one-by-one to make sure
    #     they work since ...
    # (B) They are not idempotent
    # (C) Check /etc/fstab after each one.  They should be 
    # pointing to the appropriate directory in your chroot
    
    # Set up bind mounts for the WSL generated sockets and files:
    sudo sh -c 'echo "/mnt/wsl $PWD/mnt/wsl none bind 0 0" >> /etc/fstab'
    sudo sh -c 'echo "/mnt/wslg $PWD/mnt/wslg none bind 0 0" >> /etc/fstab'
    #sudo sh -c 'echo "/run/WSL $PWD/run/WSL none bind 0 0" >> /etc/fstab' # Currently causes issues
    
    # Create fstab entries for the necessary filesystems.  For
    # the most part, we do this by finding the entry in 
    # /etc/mtab that WSL generated, copying that over to
    # /etc/fstab, and substituting the chroot path.
    
    sudo sh -c "grep '^drvfs[[:space:]]\+/mnt/c\W' /etc/mtab | sed \"s-\(/mnt/c\)-${PWD}\1-\" >> /etc/fstab"
    sudo sh -c "grep '^none[[:space:]]\+/dev[[:space:]]' /etc/mtab | sed \"s-\(/dev\)-${PWD}\1-\" >> /etc/fstab"
    sudo sh -c "grep '^proc[[:space:]]\+/proc[[:space:]]' /etc/mtab | sed \"s-\(/proc\)-${PWD}\1-\" >> /etc/fstab"
    sudo sh -c "grep '^devpts[[:space:]]\+/dev/pts[[:space:]]' /etc/mtab | sed \"s-\(/dev/pts\)-${PWD}\1-\" >> /etc/fstab"
    sudo sh -c "grep '^sysfs[[:space:]]\+/sys[[:space:]]' /etc/mtab | sed \"s-\(/sys\)-${PWD}\1-\" >> /etc/fstab"
    sudo sh -c "grep '^binfmt_misc[[:space:]]\+/proc/sys/fs/binfmt_misc[[:space:]]' /etc/mtab | sed \"s-\(/proc/sys/fs/binfmt_misc\)-${PWD}\1-\" >> /etc/fstab"
    
    # Mount these newly added entries in `/etc/fstab`.  Only needed once -- From here on out, they will automount when you restart the WSL instance:
    sudo mount -a
    
  • 这里有一件事不太好用。我们似乎无法/run/WSL通过进行绑定挂载/etc/fstab。我认为这是由于时间问题——WSL 可能尚未完成原始的挂载/run/WSL,因此我们还无法对其进行绑定挂载。尝试这样做将导致 WSL 启动时出错。此错误并不致命。

    您有多种选择。您可以:* 运行上面注释掉的行以生成 fstab 条目,处理错误,然后sudo mount -a在重新启动 WSL 后运行(或将其添加到启动文件)* 只需sudo mount --bind /run/WSL/ $PWD/run/WSL/在 WSL 重新启动后运行(从 chroot 根目录内部)(或将其添加到启动文件)。

启动 chroot:

sudo chroot $PWD env WSL_INTEROP="$WSL_INTEROP" DISPLAY="$DISPLAY" WAYLAND_DISPLAY="$WAYLAND_DISPLAY" XDG_RUNTIME_DIR="$XDG_RUNTIME_DIR" /usr/bin/bash

这会在启动 shell 之前用必要的环境变量填充环境。您可能还想映射其他变量,这很容易。

我建议apt update先启动。这至少会告诉您 DNS 解析是否正常工作。如果没有,请检查/etc/resolv.conf符号链接。

其他启动替代方案包括创建与 WSL 实例同名的用户,然后:

sudo chroot $PWD env WSL_INTEROP="$WSL_INTEROP" DISPLAY="$DISPLAY" WAYLAND_DISPLAY="$WAYLAND_DISPLAY" XDG_RUNTIME_DIR="$XDG_RUNTIME_DIR" runuser -u $USER /usr/bin/bash

答案2

@NotTheDr01ds 答案的扩展。设置以下变量以使音频在 chroot 环境中工作。

PULSE_SERVER="/mnt/wslg/PulseServer"

相关内容