18

概述

我试图让 XQuartz 在 OSX 上工作,这样我就可以通过 Docker 进行 X11 转发。我正在按照此处的说明进行操作。我相信我的问题可能只由第一部分回答,但为了以防万一(为了避免 XY 问题),我也提供了第二部分。

安装

我已经通过自制软件安装了它,通过brew cask install xquartz. 那我open -a XQuartz就开始吧。

本地 xterms

测试一下,如果我尝试打开一个xterm,它不起作用:

MacBook-Pro:opencv-gui csaftoiu$ xterm
xterm: Xt error: Can't open display: /private/tmp/com.apple.launchd.3wncZULdXC/org.macosforge.xquartz:0

但是,伪文件存在:

MacBook-Pro:opencv-gui csaftoiu$ echo $DISPLAY
/private/tmp/com.apple.launchd.3wncZULdXC/org.macosforge.xquartz:0
MacBook-Pro:opencv-gui csaftoiu$ ls -alh $DISPLAY
srw-rw-rw-  1 csaftoiu  wheel     0B May  6 21:12 /private/tmp/com.apple.launchd.3wncZULdXC/org.macosforge.xquartz:0

可以通过 XQuartz 打开一个 xterm。然后:

bash-3.2$ echo $DISPLAY
:0

此值也适用于常规 OSX:

$ DISPLAY=:0 xterm
# opens xterm, waits for it to finish
$

以下不起作用,但根据此处的答案不确定为什么:

xterm: Xt error: Can't open display: localhost:0
MacBook-Pro:opencv-gui csaftoiu$ DISPLAY=127.0.0.1:0 xterm
xterm: Xt error: Can't open display: 127.0.0.1:0
MacBook-Pro:opencv-gui csaftoiu$ DISPLAY=`ipconfig getifaddr en0`:0 xterm
xterm: Xt error: Can't open display: 192.168.1.15:0

请注意,xinit由于某种原因确实有效:

$ xinit

xinit: XFree86_VT property unexpectedly has 0 items instead of 1
# opens xterm, waits for it to finish
xinit: connection to X server lost

waiting for X server to shut down

问题 1:XQuartz 实际上在听什么?


使用 socat 进行 Docker 转发

无论如何,继续前进,此socat命令不起作用:

MacBook-Pro:opencv-gui csaftoiu$ socat TCP-LISTEN:6000,reuseaddr,fork UNIX-CLIENT:\"$DISPLAY\"

运行它,从另一个窗口我做:

MacBook-Pro:opencv-gui csaftoiu$ docker run --rm -it -e DISPLAY=`ipconfig getifaddr en0`:0 ubuntu:14.04 bash
root@912eec31b8cb:/# apt-get update && apt-get install xterm
... such install, wow ...
root@912eec31b8cb:/# xterm
Warning: This program is an suid-root program or is being run by the root user.
The full text of the error or warning message cannot be safely formatted
in this environment. You may get a more descriptive message by running the
program as a non-root user or by removing the suid bit on the executable.
xterm: Xt error: Can't open display: %s
root@912eec31b8cb:/# echo $DISPLAY
192.168.1.15:0

socat窗口我得到:

2016/06/14 21:08:15 socat[24289] E connect(5, LEN=68 AF=1 "/private/tmp/com.apple.launchd.3wncZULdXC/org.macosforge.xquartz:0", 68): Connection refused

我也不能使用有效的 DISPLAY 变量:

MacBook-Pro:opencv-gui csaftoiu$ socat TCP-LISTEN:6000,reuseaddr,fork UNIX-CLIENT:\":0\"
2016/06/14 21:09:43 socat[24309] E connect(5, LEN=4 AF=1 ":0", 4): No such file or directory

现在,这不是 UNIX-CLIENT IP。但是,我不知道连接到什么。 DISPLAY=:0它肯定不是端口 6000,因为那是它曾经监听的端口。如果我将其更改为6005, 转发到6000, 并$(ipconfig getifaddr en0):5改为 Docker 容器 DISPLAY , 那么连接当然会被拒绝:

$ socat TCP-LISTEN:6005,reuseaddr,fork TCP:localhost:6000
2016/06/14 21:20:32 socat[25379] E connect(8, LEN=16 AF=2 127.0.0.1:6000, 16): Connection refused

问题2:如何从这里着手?

4

5 回答 5

23

重新安装 XQuartz 后我没有重新启动。我重新启动,现在它可以工作了。:)。

于 2016-06-15T04:38:39.590 回答
15

Docker for Desktop MacOS 2018+ 中的 Dockerized UI 应用程序。于 2021 年更新。

经历了所有的痛苦,以获得最简单的版本,它不依赖于检查端口、IP 等......就是这样。

  • 运行版本XQuartz 2.7.11 (xorg-server 1.18.4)
  • 码头工人版本docker version 18.06.1-ce

确保安装 XQuartz(更新为2021 change

$ brew install socat
$ brew install --cask xquartz
  • 不要忘记关闭注销并重新登录。

注意:此时,请确保重新启动您的主机(例如 MacOS)。以下错误与您不这样做有关:E connect(5, LEN=2 AF=1 "<anon>", 2): Invalid argument

$ socat TCP-LISTEN:6000,reuseaddr,fork UNIX-CLIENT:\"$DISPLAY\"
2021/04/04 17:28:58 socat[40606] E connect(5, LEN=2 AF=1 "<anon>", 2): Invalid argument

指示

  • 您将需要打开 2 个终端:一个用于带显示的 socat,另一个用于运行 UI 容器。

1.关闭任何6000

在新终端上,验证端口 6000 上是否有任何东西在运行

$ lsof -i TCP:6000
$

如果有任何东西,只需终止该进程

2.关闭任何6000

在该端口上打开一个套接字并保持终端打开

$ socat TCP-LISTEN:6000,reuseaddr,fork UNIX-CLIENT:\"$DISPLAY\"

3.验证6000是否打开

在新终端中,验证它是否已打开

$ lsof -i TCP:6000
COMMAND   PID     USER   FD   TYPE             DEVICE SIZE/OFF NODE NAME
socat   29298 marcellodesales    5u  IPv4 0xe21e43ca9d99bf1d      0t0  TCP *:6000 (LISTEN)

4. 构建并运行简单的 UI 应用程序

$ cat Dockerfile.eyes

FROM debian:latest
RUN apt-get update && apt-get install -y x11-apps
RUN rm -rf /tmp/* /usr/share/doc/* /usr/share/info/* /var/tmp/*
RUN useradd -ms /bin/bash user
ENV DISPLAY :0
USER user
ENTRYPOINT ["/bin/sh", "-c", "$0 \"$@\"", "xeyes"]

$ docker build -t eyes -f Dockerfile.eyes .

神奇的是使用来自 Docker 的变量。只需使用-e DISPLAY=docker.for.mac.host.internal:0技巧,因为它将指向内部 IP 地址并将其提供给 docker 映像。港口前锋将发挥它的魔力。

$ docker run -ti --rm -e DISPLAY=docker.for.mac.host.internal:0 eyes

在此处输入图像描述

我注意到此时 XQuartz 已自行打开到同一个端口

$ lsof -i TCP:6000
COMMAND   PID     USER   FD   TYPE             DEVICE SIZE/OFF NODE NAME
socat   29298 marcellodesales    5u  IPv4 0xe21e43ca9d99bf1d      0t0  TCP *:6000 (LISTEN)
X11.bin 29462 marcellodesales    8u  IPv6 0xe21e43ca7cdb1135      0t0  TCP *:6000 (LISTEN)

5. 盈利并运行更多应用程序

$ docker run -e DISPLAY=docker.for.mac.host.internal:0 jess/tor-browser

在此处输入图像描述

$ docker run -e DISPLAY=docker.for.mac.host.internal:0 batmat/docker-eclipse

在此处输入图像描述

于 2018-11-29T21:55:23.233 回答
2

对于 OS X 10.6.3 及更高版本,根据XQuartz 2.7.11 指令

如果这是您第一次安装 XQuartz,您可能希望注销并重新登录。这将更新您的 DISPLAY 环境变量以指向 XQuartz.app 而不是 X11.app。如果您希望继续使用 X11.app 作为默认服务器(您仍然可以手动启动 XQuartz.app),您需要使用launchctl(1)禁用 /Library/LaunchAgents/org.macosforge.xquartz.startx.plist .

在我的 macOS High Sierra 上安装XQuartz 2.7.11后,退出我的 Mac 并再次登录就足以通过我的 MacOS 终端运行。但是,您可以通过打开 XQuartz Terminal 应用程序( XQuartz > Applications > Terminal)并从那里运行您的 X 应用程序来避免注销和登录。例如:

在此处输入图像描述

接着

bash-3.2$ xclock &
于 2018-03-14T01:42:12.030 回答
2

我需要退出终端,然后重新启动它才能让它工作。

于 2017-02-14T11:22:38.253 回答
-1

我使用此代码将帮助您在 macos Big sur https://apple.stackexchange.com/questions/411619/how-to-make-dia-which-uses-x11-xquartz-work

export DISPLAY=:0 # 修复“无法打开显示”。export LANG="en_US.UTF-8" # 修复恼人的 Xterm 窗口打开。

执行“$CWD/dia-bin”--集成

于 2021-09-22T21:49:29.440 回答