
最早动这个念头是因为我人在外地却需要操作实验室里那台装着Ubuntu 20.04桌面的机器。旁边还坐着一位同事他随时要看我屏幕上的运行结果我不能另开一个独立会话把他晾在一边。试过TeamViewer、向日葵、XRDP体验都不算顺商业软件在Linux下动不动掉线XRDP默认又会新建一个和物理桌面完全无关的虚拟会话。最后换到X11VNC问题才算真正解决。这篇就把我在Ubuntu 20.04 Desktop上配置X11VNC远程桌面的完整过程写清楚——从安装到自启动、从参数含义到安全加固、再到实际排错适合需要在局域网远程控制Linux桌面、或者在外面通过跳板机连回办公电脑的人参考。1. 为什么偏偏选X11VNC本地会话与虚拟会话的本质差异1.1 先搞清楚Linux远程桌面的两条技术路线Linux下的远程桌面方案看着很多但底层逻辑其实就两条。一类是“另起炉灶”在后台创建一个全新的、和物理桌面独立的图形会话比如XRDP、TigerVNC Server、X2Go都是这个思路。你远程连上去看到的是一套干干净净的新桌面和坐在机器前面的人看到的画面完全无关。另一类是“现场镜像”直接附加到当前正在运行的X11显示服务上把物理屏幕上已经存在的画面实时转发给远端X11VNC就是这类方案的代表。这两条路线没有绝对的优劣但选错会很痛苦。如果你只是一个人安安静静地远程办公独立会话反而更舒服因为它不会打扰占用物理桌面的人。但如果机器旁边还坐着别人或者你远程操作的软件依赖当前物理会话里的显卡、加密狗、特殊显示环境独立会话就麻烦了——远处的人看到的和你本地看到的东西对不上协作时很容易一脸懵。X11VNC是一个VNC服务端但它不启动任何新的桌面进程只是挂在你已有的X11显示服务上把当前的帧缓冲内容通过VNC协议推送给客户端。这个过程有一个非常关键的属性所见即所得。你在远程看到的就是物理屏幕上正在显示的内容包括已经打开的窗口、正在跑的进度条、弹窗和警告。1.2 主流方案横向对比我在Ubuntu 20.04上实际用过一轮把主要方案的特性整理成了下面这张表方便直接对照。方案会话逻辑Ubuntu 20.04适配资源占用适合场景X11VNC镜像现有X11会话好apt直接安装稳定中低远程操作物理桌面、远程协助、演示TigerVNC Server独立Xvnc虚拟会话可以但需自行配置桌面管理器中无头服务器跑轻量桌面XRDP默认新建独立Xorg会话可装但和物理桌面不同步中高Windows RDP客户端直连LinuxTeamViewer/向日葵等自带会话管理可用但偶发掉线、响应慢较高跨平台临时远程协助这里要特别提醒XRDP虽然名字里带个RDP看着很亲切但它在Ubuntu 20.04上默认行为和Windows的远程桌面有本质区别。Windows的RDP可以直接接管当前桌面会话而Linux的XRDP通常给你的是一个新会话。如果你的需求是“远程看到和本地一模一样的桌面”XRDP不是你要找的东西。1.3 为什么不是TigerVNCTigerVNC是Linux上很常见的VNC服务端但它和X11VNC的适用场景不一样。TigerVNC Server在无显示器、无图形登录环境的服务器上更顺手它负责把远程桌面会话跑起来而X11VNC的强项是——这台机器已经有人登录了图形桌面你想把当前这个会话共享出去。Ubuntu 20.04桌面版最常见的状态恰恰是后者本地用户登录了GNOME桌面你需要远程接管它。所以我的结论很简单已经在跑物理桌面的机器远程控制首选X11VNC没有显示器的服务器才需要考虑启动独立会话的方案。认清这个区别后面所有配置都不会走偏。2. 安装之前先确认会话类型Wayland还是Xorg决定成败2.1 这一步不做后面大概率黑屏Ubuntu 20.04虽然默认登录会话还是Xorg但系统已经在推广Wayland。如果当前用户登录的是Wayland会话X11VNC会直接连不上或者连上后只有一片灰因为Wayland本身不暴露X11的帧缓冲接口x11vnc根本没地方挂载。先花十秒确认当前会话类型echo $XDG_SESSION_TYPE loginctl show-session $(loginctl | grep $(whoami) | awk {print $1}) -p Type输出应该是x11。如果看到的是wayland请在登录界面点右上角齿轮图标切换到“Ubuntu on Xorg”再登录。这个操作只需要做一次后续默认都会走Xorg。另外用NVIDIA闭源驱动的机器Wayland会话下的VNC体验更差不仅黑屏偶尔还会把本地物理屏幕搞花。所以我的建议是这台机器要长期做远程控制就直接固定在Xorg会话。2.2 安装x11vnc版本确认一下Ubuntu 20.04的软件源里x11vnc版本是0.9.16够用且稳定不需要从源码编译。sudo apt update sudo apt install -y x11vnc x11vnc -version能看到版本号就没有问题。如果你想用后续文章会提到的SSL加密特性需要确认包是否编译了SSL支持。仓库里的版本一般都有不过我最常用的还是SSH隧道方案下面会细说。2.3 设置独立的VNC密码文件VNC密码和系统登录密码是两回事建议单独设置一个只有远程连接用的复杂口令。sudo mkdir -p /etc/x11vnc sudo x11vnc -storepasswd 你的VNC密码 /etc/x11vnc/passwd sudo chmod 600 /etc/x11vnc/passwd这里有个大多数人不知道的细节传统VNC协议在认证阶段只比较密码的前8个字符。也就是说你设置了一个20位的长密码实际生效的可能是前8位。这不是x11vnc的bug而是RFB协议老底子留下的限制。所以不要把VNC密码当作唯一防线配合后续的防火墙或SSH隧道才是正确姿势。3. 一条启动命令、一个systemd服务让X11VNC开机就在3.1 先手工启动一次把基础功能跑通不要一上来就写systemd服务先手工启动一次确认命令本身没问题。sudo x11vnc -display :0 -auth guess -forever -loop -noxdamage -repeat \ -rfbauth /etc/x11vnc/passwd -rfbport 5900 -shared -o /var/log/x11vnc.log终端里没有报错后用任意VNC客户端连一次。如果能直接看到桌面再进行下一步。如果连不上优先看日志最后几行sudo tail -20 /var/log/x11vnc.log最常见的错误是XOpenDisplay failed说明x11vnc找不到X显示服务要么-display参数不对要么-auth没有指对授权文件。3.2 逐个参数搞清楚配置才不会改错很多教程直接甩一条命令让你复制一旦出问题就抓瞎。这里把关键参数都拆开说明。-display :0告诉x11vnc要挂到哪个X显示上。Ubuntu桌面默认第一个图形会话是:0基本不用改。-auth guess自动猜测Xauthority文件的路径。这条不加root都救不了你x11vnc会因为无法通过X授权认证而拒绝工作。-forever客户端断开后进程不退出继续保持监听状态等下一次连接。-loop如果显示连接失败或者进程异常退出自动重试。开机后桌面环境还没起来时特别有用。-noxdamage禁用X DAMAGE扩展。NVIDIA闭源驱动下我强烈建议直接加上否则远程画面很容易出现残影、局部不刷新。-repeat允许键盘重复事件。不加的话你远程按住方向键或退格键会发现毫无反应。-rfbauth指定VNC密码文件。-rfbport 5900监听端口默认就是5900。-shared允许多个VNC客户端同时连接。团队协作时很有用代价是带宽会分摊。-o /var/log/x11vnc.log写日志。3.3 用systemd管住它而不是写进autostart为什么不推荐把启动命令写进~/.bashrc或者桌面环境的“启动应用程序”因为autostart只在用户登录后才会触发而且用户退出登录、桌面进程结束x11vnc也会跟着死掉。systemd服务则可以在开机后立刻启动进程独立于你的登录会话崩溃了还能自动拉起来。创建服务文件sudo vim /etc/systemd/system/x11vnc.service[Unit] DescriptionX11VNC Remote Desktop Server Aftergraphical.target [Service] Typesimple EnvironmentDISPLAY:0 ExecStart/usr/bin/x11vnc -display :0 -auth guess -forever -loop -noxdamage -repeat -rfbauth /etc/x11vnc/passwd -rfbport 5900 -shared -o /var/log/x11vnc.log Restarton-failure RestartSec5 [Install] WantedBymulti-user.target然后启用sudo systemctl daemon-reload sudo systemctl enable --now x11vnc systemctl status x11vnc这里有个实践经验让x11vnc以root身份跑最省事。因为root能读取所有用户的Xauthority文件-auth guess基本都能猜中。如果换成普通用户运行就要额外处理权限很容易踩坑。3.4 GDM登录界面能不能远程连很多人配置完成后发现一个尴尬问题开机后停在登录界面远程连过去要么黑屏要么连接被拒绝。这是因为GDM登录界面运行在独立的显示服务器上而x11vnc挂载的是用户桌面:0在还没有用户登录时:0上根本没有可共享的桌面会话。如果你确实需要重启后远程直接可用可以设置自动登录。在Ubuntu 20.04的“设置 – 用户”里打开自动登录或者修改/etc/gdm3/custom.conf[daemon] AutomaticLoginEnabletrue AutomaticLogin你的用户名注意自动登录会带来安全风险——任何人物理接触这台机器都能直接进入桌面。这个取舍要自己权衡我个人只建议在实验室、机房等可信环境里使用。4. 别让5900端口裸奔防火墙与SSH隧道两种加固姿势4.1 局域网内的最小防火墙规则VNC协议本身没有加密密码又是老式的8位DES直接把5900端口暴露到整个网络里并不安全。如果你只是在同一个局域网里用最小限度也要用UFW限制来源IP。sudo ufw allow OpenSSH sudo ufw allow from 192.168.1.0/24 to any port 5900 proto tcp sudo ufw enable第一行先放行SSH非常重要。不这么做的话一旦开启UFW现有SSH连接会立刻中断远程就再也回不去了。如果不需要其他网段访问那就不要加更宽松的规则。Ubuntu默认防火墙没启用时5900端口会监听在所有网卡上这等于告诉同一网络里的所有人“这里有VNC端口可以试”。4.2 我最推荐的方案SSH隧道加-localhost如果条件允许我最推荐的组合是把x11vnc限制为只监听本机回环地址然后通过SSH隧道访问。这样一来5900端口根本不会暴露在网络上VNC流量也被SSH加密了即使VNC密码偏弱风险也可控。修改systemd服务文件在ExecStart里加上-localhost参数ExecStart/usr/bin/x11vnc -display :0 -auth guess -forever -loop -noxdamage -repeat -rfbauth /etc/x11vnc/passwd -rfbport 5900 -shared -localhost -o /var/log/x11vnc.log然后在Windows客户端机器上建立SSH隧道ssh -L 5900:localhost:5900 用户名Ubuntu主机IPVNC客户端里连接localhost:5900即可。如果你在公司或者跨网络环境可以先把SSH端口转发到一台能访问目标机的跳板机上再做本地转发思路是一样的。走公网时绝对不要直接把5900映射出去我见过太多因为裸奔VNC导致桌面被控制、数据被翻的案例了。4.3 x11vnc其实还有SSL选项如果你不想用SSH隧道x11vnc还支持-ssl参数开启TLS加密Ubuntu仓库版一般编译了SSL支持。生成自签名证书后用-ssl启动VNC客户端连接时可以勾选“接受自签名证书”。但实测下来Windows上的RealVNC Viewer对自签名证书的处理很麻烦需要手动信任操作成本比SSH隧道高不少。所以我个人还是更喜欢-localhost SSH隧道的组合简单、可靠、生态好。5. 客户端连接实测黑屏、断连、卡顿的排查链路5.1 常用的VNC客户端怎么选不同平台上我习惯的客户端不太一样。WindowsRealVNC Viewer兼容性好解码效率也高TigerVNC Viewer也可以更轻量。macOS直接用Finder的“前往 – 连接服务器”输入vnc://IP:5900就能连不用装额外软件。Linux桌面Remmina自带的VNC插件挺好用Ubuntu上装一下就有了。连接时填IP:5900敲VNC密码就能看到桌面。如果是SSH隧道模式填localhost:5900。5.2 黑屏、灰屏、连接被拒绝我遇到最多的三种情况先后按这几个方向排查连接被拒绝先看系统服务是否还活着systemctl status x11vnc然后确认防火墙没有拦sudo ufw status。能连上但黑屏优先怀疑会话类型。确认远程机当前是Xorg会话不是Wayland。其次考虑显卡驱动问题给启动命令补上-noxdamage。如果显示器休眠了有些显卡会把输出停掉可以先本地唤醒屏幕再连。连上后立刻断开打开/var/log/x11vnc.log看日志基本都能看到线索。最常见的是密码文件权限不对或者x11vnc没有权限读Xauthority。检查/etc/x11vnc/passwd是不是600权限、服务是不是root跑的。5.3 远程卡顿、刷新不全怎么优化VNC协议是基于屏幕区域按需更新的不像RDP那样针对视频和动画做专门优化所以在网络一般的情况下卡顿会很明显。我的习惯做法是几个参数组合使用。服务端加-solid把桌面背景设成纯色。壁纸是大面积反复传输的元凶纯色背景能省很多流量。服务端加-scale 0.75把画面按比例缩小后再传输带宽立刻下降适合跨网络办公。客户端把颜色深度调到16位甚至8位颜色失真换来流畅度只看文档完全够用。别在VNC里硬开着高帧率的动画、视频这不是VNC擅长的场景。5.4 键盘乱码和鼠标偏移远程输入时字符不对多半是客户端键盘布局和服务端不一致。把客户端键盘布局临时切到US English或者在远程终端里执行setxkbmap us基本能解决。鼠标点击位置偏移则出现在客户端显示比例和服务端分辨率不匹配的时候把VNC客户端的缩放设为1:1或者Adapt模式即可。5.5 锁屏界面怎么远程解锁GNOME锁屏后VNC客户端连上去会看到锁屏界面。这时候输入VNC密码没有用需要在锁屏界面输入系统用户的登录密码才能解锁。这不是配置问题是安全设计习惯就好。6. 进阶调优画质、缓存、多显示器的取舍6.1 -ncache能在滚动长页面时救你一命x11vnc有个特色参数-ncache可以在客户端本地多缓存几帧画面。滚网页、翻代码的时候画面更新会明显流畅因为重复出现的屏幕内容不用反复传。我一般设成10-ncache 10需要提醒的是这个功能依赖客户端对x11vnc扩展编码的支持。RealVNC Viewer配合得很好但部分开源客户端可能无效。如果用了-ncache后画面出现奇怪的色块可以改小数值或者去掉。6.2 多显示器只共享主屏如果远程机器接了多台显示器x11vnc默认会把多个屏幕拼成一整块大画布推给客户端。但有时你只想让远端看主屏这时候用-clip指定捕获区域-clip 1920x10800000是主屏左上角坐标。这个参数在做临时共享、演示场景时非常实用避免对方看到一堆用不上的屏幕内容。6.3 日常运维三板斧用了很长时间x11vnc之后我养成了固定排查习惯三个命令覆盖日常运维systemctl status x11vnc sudo tail -f /var/log/x11vnc.log sudo ss -tlnp | grep 5900服务状态、实时日志、端口监听这三个信息基本能定位绝大多数问题。如果哪天远程突然连不上了第一件事就是打开日志看而不是直接重启服务——日志里往往写着真正的原因重启只会掩盖问题。6.4 假如还是想用RDP客户端我知道很多人习惯了Windows自带的远程桌面到了Linux上也希望用RDP。Ubuntu 20.04装XRDP确实能用但请记住前面说的会话逻辑默认创建的独立会话和物理桌面不同步。如果你只是想远程开一个Linux桌面界面XRDP是可以的如果你要的是“远程看到和本地屏幕完全一样的东西”那就回来用X11VNC。这两个需求不要混为一谈这也是我在开篇花那么大篇幅讲技术路线差异的原因。要说个人体会最有价值的一条经验是VNC这类方案的重心永远在于“会话模型选对”而不是那一堆参数。先把“我是要接管现有桌面还是新建独立桌面”想清楚再动手配置基本不会走弯路。x11vnc参数再多绕不开这个核心判断。