
1. 项目缘起与核心定位1.1 这个项目到底在做什么“Madeira”这个名字乍一看像是个地名但在我们这行里它指的是一套围绕FEX-Emu、Wine、DXMT构建的跨架构兼容运行方案目标很明确让 x86-64 平台的 Windows 应用和游戏能够在 ARM 架构的设备上跑起来尤其是 iOS 设备与国产 Linux 发行版这两类场景。说白了就是解决“我手头只有 ARM 设备但我想跑 x86 的 Windows 程序”这个老大难问题。我最早接触这个方向是因为身边一堆人问iOS 上能不能玩 Windows 游戏统信、麒麟上怎么装 Windows 软件这些问题背后其实是同一个技术链条——指令集翻译 Windows API 兼容 图形接口转换。Madeira 就是把这几个环节串起来的一套实践方案它不是某一个单独的软件而是一组工具的组合拳。适合谁来参考三类人一是想在 ARM Linux比如统信 UOS、麒麟上跑 Windows 应用的运维和普通用户二是对 iOS 上运行 x86 程序感兴趣的技术玩家三是想理解 FEX-Emu、Wine、DXMT 这三者怎么配合的开发者。哪怕你只是被“wine 乱码”“麒麟 wine 助手下载”这些问题折磨过这篇内容也能给你一条清晰的路径。1.2 为什么是 FEX-Emu Wine DXMT 这个组合先拆开看这三个东西各自干什么。FEX-Emu负责的是 CPU 指令集翻译。ARM 和 x86-64 的指令集完全不一样x86 程序在 ARM 上跑第一步就是要把 x86-64 指令实时翻译成 ARM 能执行的指令。FEX-Emu 就是干这个的它属于用户态模拟器性能比全系统模拟比如 QEMU 那种要好不少因为它不需要模拟整个硬件环境只翻译指令。Wine负责的是 Windows API 兼容。Windows 程序调用的是 Windows 的系统接口Linux 和 iOS 上没有这些接口Wine 就提供了一套兼容层把这些调用翻译成 POSIX 或者宿主系统的调用。Wine 不是模拟器它是“翻译层”所以理论上性能损耗比虚拟机小。DXMT负责的是图形接口转换。Windows 游戏大量使用 Direct3D而 Linux 上主流是 Vulkan 和 OpenGL。DXMT 的作用就是把 D3D 调用转成 Metal在 macOS/iOS 上或者 Vulkan在 Linux 上让游戏能正常渲染。这三者叠在一起逻辑链条就是FEX-Emu 翻译 CPU 指令 → Wine 翻译系统调用 → DXMT 翻译图形调用。缺一环Windows 程序就跑不起来或者跑不顺。我试过只用 Wine 不用 FEX-Emu在 ARM 上直接报“无法执行二进制文件”也试过只用 FEX-Emu 不用 Wine程序能启动但一调用 Windows API 就崩。所以这个组合不是随便选的是环环相扣的。1.3 这套方案解决了哪些实际痛点从热搜词能看出来大家的痛点非常具体。“wine 乱码”是编码问题“麒麟 wine 助手下载”是找不到靠谱的安装源“wine deepin 无法下载”是包管理出了问题“统信 wine windows 兼容组件下载”是不知道该装哪个组件。这些问题我在实操里全踩过。Madeira 这套方案的价值在于它把这些零散的问题整合成了一条可复现的流程。比如乱码问题根因通常是 Wine 的字体配置和 locale 设置不对而不是 Wine 本身坏了。再比如“无法下载”很多时候是源里没有对应的包需要手动配置或者用兼容组件替代。这些细节官方文档往往一笔带过但对实际使用者来说就是拦路虎。2. 核心组件拆解与选型逻辑2.1 FEX-Emu 的定位与版本选择FEX-Emu 是目前 ARM 上跑 x86-64 程序比较成熟的用户态模拟器之一。它的核心机制是JIT 编译程序运行的时候把 x86-64 指令块动态翻译成 ARM64 指令块然后缓存起来下次遇到同样的指令块就直接用缓存。这个设计让它在重复执行同一段代码时性能接近原生。版本选择上我建议用FEX-Emu 的最新稳定版而不是追最新的开发版。原因很简单开发版经常改配置格式你今天调好的参数明天升级可能就失效了。稳定版的 rootfs 和配置模板更靠谱。安装方式上Linux 下优先用发行版自带的包如果没有就用官方提供的 rootfs 压缩包手动解压配置。注意FEX-Emu 对内核版本有要求太老的内核可能不支持它用到的某些系统调用。统信和麒麟的用户尤其要注意先确认内核版本再决定装哪个版本的 FEX-Emu。2.2 Wine 的兼容层原理与常见分支Wine 的全称是“Wine Is Not an Emulator”它不模拟硬件而是直接实现 Windows API。当 Windows 程序调用CreateFile时Wine 把它转成 Linux 的open调用MessageBox时Wine 用宿主系统的窗口系统画一个对话框。Wine 有几个常见分支官方版 Wine、Wine-Staging包含更多实验性补丁、ProtonValve 为 Steam 游戏优化的版本。在 Madeira 这个场景里我一般推荐Wine-Staging因为它对游戏和新版 Windows API 的支持更好。但如果你追求稳定官方稳定版也够用。“麒麟 wine 助手”这类工具本质上是对 Wine 的封装帮你自动配置前缀prefix、安装依赖组件比如 .NET、Visual C 运行库。用助手的好处是省事坏处是出问题时不好排查因为你不知道它背后改了什么。我的建议是先用助手跑通再逐步了解它做了什么这样既省时间又能学到东西。2.3 DXMT 的角色与图形栈适配DXMT 是 Direct3D 到 Metal 的翻译层主要用在 Apple 生态里。它的工作是把 D3D11 和 D3D12 的调用翻译成 Metal 调用。为什么不用 DXVK因为 DXVK 是把 D3D 转成 Vulkan而 iOS 和 macOS 上 Vulkan 支持不好Metal 才是原生图形接口。在 Linux 上图形栈的选择就多了可以用 DXVK 转 Vulkan也可以用 OpenGL 直通。Madeira 方案里Linux 端我一般用DXVK Vulkan因为 Vulkan 在国产 Linux 上的驱动支持越来越好了。iOS 端则必须用 DXMT因为 Metal 是唯一选择。这里有个关键点图形翻译层的性能损耗比 CPU 翻译层更明显。FEX-Emu 翻译指令的损耗通常在 20%-40%而图形翻译如果没配好帧率可能直接砍半。所以 DXMT 或 DXVK 的配置参数比如缓存大小、异步编译开关一定要调优。2.4 三者如何协同工作用一个实际例子说明。假设你要在 ARM Linux 上跑一个 Windows 游戏你双击游戏 exe系统调用 FEX-Emu 来加载这个 x86-64 可执行文件。FEX-Emu 把 x86-64 指令翻译成 ARM64 指令游戏开始执行。游戏调用 Windows API比如创建窗口、读取文件Wine 把这些调用转成 Linux 系统调用。游戏调用 Direct3D 渲染画面DXVK 把 D3D 调用转成 VulkanVulkan 驱动再交给 GPU。如果游戏用到 .NET 或 VC 运行库Wine 的前缀里需要预先装好这些组件。整个链条里任何一环配置不对游戏就黑屏、闪退或者乱码。所以 Madeira 的实操重点不是“装哪个软件”而是“怎么把这几环的配置对齐”。3. 实操部署全流程3.1 环境准备与依赖检查动手之前先把环境摸清楚。以下命令在统信 UOS 和麒麟上基本通用# 查看内核版本 uname -r # 查看 CPU 架构 uname -m # 查看发行版信息 cat /etc/os-release # 查看已安装的 Wine 相关包 dpkg -l | grep -i wine # 查看 Vulkan 支持 vulkaninfo | head -20内核版本建议5.15 以上低于这个版本 FEX-Emu 可能跑不起来。CPU 架构确认是aarch64。Vulkan 如果没装先装mesa-vulkan-drivers和vulkan-tools。依赖方面需要装这些基础库sudo apt install -y libgl1-mesa-dri libglx-mesa0 libvulkan1 \ mesa-vulkan-drivers vulkan-tools libgnutls30 libasound2 \ libpulse0 libdbus-1-3 fontconfig提示国产 Linux 的源有时候不全如果某个包找不到去对应发行版的兼容组件仓库里找或者用官方提供的离线包手动安装。3.2 FEX-Emu 的安装与配置FEX-Emu 的安装有两种方式。第一种是用包管理器# 添加 FEX-Emu 官方源以 Debian 系为例 sudo add-apt-repository ppa:fex-emu/fex sudo apt update sudo apt install fex-emu第二种是手动解压 rootfs# 下载 rootfs 压缩包后解压 mkdir -p ~/fex-rootfs tar -xzf FEX-rootfs.tar.gz -C ~/fex-rootfs # 配置环境变量 export FEX_ROOTFS~/fex-rootfs export PATH$FEX_ROOTFS/usr/bin:$PATH配置方面FEX-Emu 的配置文件通常在~/.fex-emu/Config.json。关键参数参数作用推荐值RootFS根文件系统路径指向解压目录ThunkHostLibs宿主库路径/usr/lib/aarch64-linux-gnuThunkGuestLibs客户库路径rootfs 内的库目录SMCChecks系统调用检查默认即可TSODisable禁用 TSO 内存模型视程序而定TSO 这个参数值得说一下。x86 有 TSOTotal Store Order内存模型ARM 是弱内存模型。FEX-Emu 默认会模拟 TSO但这会带来性能损耗。如果程序对内存顺序不敏感可以关掉 TSO 换性能。我实测下来关掉 TSO 后某些游戏帧率能提升 10% 左右但个别程序会崩所以要逐个测试。3.3 Wine 前缀的创建与组件安装Wine 的前缀prefix是一个独立的目录里面模拟了 C 盘、注册表和 Windows 目录结构。每个程序最好用独立的前缀避免互相干扰。# 创建 64 位前缀 WINEARCHwin64 WINEPREFIX~/.wine-madeira winecfg # 安装常用组件 WINEPREFIX~/.wine-madeira winetricks corefonts vcrun2019 dotnet48winetricks是必装工具它能帮你自动下载安装各种 Windows 运行库。corefonts解决字体问题vcrun2019是 VC 运行库dotnet48是 .NET Framework 4.8。乱码问题的根因就在这里。Wine 默认的字体映射不对中文程序会显示成方块或问号。解决办法是# 安装中文字体 WINEPREFIX~/.wine-madeira winetricks cjkfonts # 或者手动复制字体到前缀 cp /usr/share/fonts/truetype/wqy/wqy-microhei.ttc \ ~/.wine-madeira/drive_c/windows/Fonts/然后在winecfg的“显示”选项卡里把所有字体替换成WenQuanYi Micro Hei或Noto Sans CJK SC。这一步做完大部分乱码问题就解决了。3.4 DXMT/DXVK 的部署与参数调优Linux 端用 DXVK# 下载 DXVK 最新版 wget https://github.com/doitsujin/dxvk/releases/download/v2.3/dxvk-2.3.tar.gz tar -xzf dxvk-2.3.tar.gz # 安装到 Wine 前缀 cd dxvk-2.3 WINEPREFIX~/.wine-madeira ./setup_dxvk.sh installiOS 端用 DXMT需要把 DXMT 的 dylib 文件放到 Wine 的库目录里并配置WINEDLLOVERRIDES环境变量export WINEDLLOVERRIDESd3d11n,b;dxgin,bDXVK 的关键配置在dxvk.conf里配置项作用推荐值dxvk.numCompilerThreads编译线程数CPU 核心数的一半dxvk.enableAsync异步编译Truedxvk.maxChunkSize最大块大小默认dxgi.maxFrameLatency最大帧延迟1dxvk.enableAsync这个参数特别重要。它让着色器编译在后台异步进行避免游戏卡顿。我试过开关这个参数开关后《巫师 3》的卡顿明显减少。3.5 完整启动脚本与验证把上面的步骤串起来写一个启动脚本#!/bin/bash export FEX_ROOTFS~/fex-rootfs export WINEPREFIX~/.wine-madeira export WINEDLLOVERRIDESd3d11n,b;dxgin,b export DXVK_CONFIG_FILE~/dxvk.conf export FEX_TSO0 cd ~/games fex-emu -c ~/.fex-emu/Config.json ./game.exe验证是否成功看几个指标程序能不能启动、窗口能不能正常显示、中文有没有乱码、帧率是否可接受。如果启动就崩先看终端报错如果窗口黑屏检查 DXVK 日志如果乱码回去检查字体配置。4. 常见问题与排查实录4.1 Wine 乱码问题的系统排查乱码是最高频的问题没有之一。排查顺序如下确认字体是否安装fc-list | grep -i cjk看有没有中文字体。确认 Wine 字体映射打开winecfg在“显示”里看字体替换设置。确认 localeecho $LANG应该是zh_CN.UTF-8或en_US.UTF-8。确认程序编码有些老程序用 GBK 编码需要设置LC_ALLzh_CN.GBK。我遇到过一种情况字体都装了locale 也对但还是乱码。最后发现是程序的注册表里字体设置指向了一个不存在的字体。解决办法是在winecfg里强制替换所有字体为已安装的中文字体。4.2 麒麟/统信下 Wine 助手下载与安装失败“麒麟 wine 助手下载”这个热搜词背后是很多人找不到靠谱的下载源。我的经验是优先用系统自带的软件商店如果没有去发行版官方的兼容组件仓库找。统信和麒麟都有自己的 Windows 兼容组件包名字可能叫deepin-wine或kylin-wine。如果包管理器报错先更新源sudo apt update sudo apt install -f如果还是不行检查是不是架构不匹配。有些兼容组件只有 x86 版本ARM 上装不了。这时候要么找 ARM 版本要么用 FEX-Emu 官方 Wine 的组合替代。4.3 图形渲染异常与帧率优化图形问题表现多样黑屏、花屏、闪退、帧率低。排查思路黑屏看 DXVK 日志通常是着色器编译失败或 Vulkan 驱动不支持某个特性。花屏可能是显存不足或纹理格式不支持试试降低游戏画质。闪退看 Wine 的报错输出常见的是缺少某个 DLL。帧率低先确认是不是 CPU 瓶颈FEX-Emu 翻译损耗再确认是不是 GPU 瓶颈。帧率优化上我总结了几条关掉 TSO、开异步着色器编译、降低分辨率、关闭垂直同步。这几条下来大部分游戏能从“不能玩”变成“能玩”少数能从“能玩”变成“流畅”。4.4 常见问题速查表问题现象可能原因排查方法解决方案程序无法启动FEX-Emu 未配置看终端报错检查 Config.json中文乱码字体缺失fc-list 检查安装 CJK 字体并替换黑屏DXVK 未安装看 DXVK 日志安装 DXVK 并配置闪退缺少运行库Wine 报错winetricks 安装组件帧率低TSO 开启对比测试关闭 TSO无法下载组件源不全apt 报错手动下载离线包窗口无响应图形驱动问题vulkaninfo更新 Mesa 驱动提示排查问题时养成看日志的习惯。Wine 的日志用WINEDEBUGall打开DXVK 的日志在游戏目录下的.log文件里。日志里的报错信息比任何猜测都靠谱。4.5 几个容易忽略的细节第一个细节是路径问题。Wine 对中文路径和空格路径支持不好游戏最好放在纯英文、无空格的目录里。我见过有人把游戏放在“我的游戏”文件夹里结果怎么都启动不了改成~/games就好了。第二个细节是权限问题。FEX-Emu 和 Wine 都需要对某些目录有读写权限如果装在系统目录里普通用户可能没权限。建议全部装在用户目录下。第三个细节是版本匹配。FEX-Emu、Wine、DXVK 的版本要互相兼容。我试过用最新版 FEX-Emu 配老版 Wine结果系统调用对不上程序直接崩。所以升级的时候要一起升别只升一个。5. 性能调优与进阶技巧5.1 CPU 翻译层的性能压榨FEX-Emu 的性能损耗主要来自指令翻译和 TSO 模拟。除了关 TSO还有几个参数可以调Multiblock开启多块翻译减少翻译次数。SMCChecks关闭自修改代码检查提升性能但可能影响兼容性。HalfBarrier半屏障模式平衡性能和正确性。这些参数在Config.json里配置。我的建议是逐个开启测试找到性能和稳定性的平衡点。不要一次全开否则出问题不知道是哪个参数导致的。5.2 图形层的帧率优化DXVK 的异步编译是最大的性能开关。开启后着色器编译在后台线程进行主线程不会卡住。但异步编译有个副作用某些着色器可能编译不及时导致画面短暂异常。如果游戏对画面一致性要求高可以关掉。另一个技巧是限制帧率。ARM 设备的 GPU 性能有限让游戏跑满帧反而会导致过热降频。用dxgi.maxFrameLatency和dxgi.syncInterval限制帧率能让帧率更稳定。5.3 iOS 场景的特殊处理iOS 上跑 x86 程序限制比 Linux 多得多。首先是开发者模式iOS 16 以后需要在设置里手动开启。其次是证书签名没有签名的应用无法安装。再就是图形接口iOS 只能用 Metal所以必须用 DXMT。iOS 上的 Wine 通常是通过某种容器应用实现的你需要把 exe 文件和依赖库打包进去。这个过程比较繁琐而且受 iOS 版本影响很大。我的建议是先确认你的 iOS 版本和设备支持再动手。另外iOS 上的性能损耗比 Linux 更大因为 Metal 翻译层的开销更高。5.4 长期维护与版本升级策略这套方案涉及多个组件升级的时候要小心。我的策略是保持一个稳定可用的版本组合不轻易升级。如果非要升级先备份配置和前缀升级后逐个测试。具体来说FEX-Emu 和 Wine 的版本要匹配DXVK 的版本要跟 Wine 匹配。升级前先查一下社区有没有人踩过坑。我一般会在虚拟机里先试一遍确认没问题再在主系统上升级。6. 个人实操体会这套方案我从头到尾搭过不下十次每次都有新坑。最大的体会是不要追求一步到位要分阶段验证。先让 FEX-Emu 能跑一个简单的 x86 程序再加 Wine 跑一个简单的 Windows 程序最后加 DXVK 跑一个游戏。每加一层验证一次。这样出问题的时候你能快速定位是哪一层的锅。另一个体会是社区比文档靠谱。FEX-Emu、Wine、DXVK 的官方文档往往只讲“怎么装”不讲“装完出问题怎么办”。遇到问题去对应的 issue 区和论坛搜大概率有人遇到过同样的问题。我解决乱码问题的关键线索就是在论坛里看到有人说“字体替换要覆盖所有字体项”而不是只改默认字体。最后分享一个小技巧用快照或容器隔离环境。每次折腾之前先给系统打个快照或者用 Docker 容器跑。这样搞崩了能快速回滚不用重装系统。我早期没做隔离搞崩过两次系统重装花了大半天血的教训。