答案1
Xterm已经/dev/ptmx
打开了,但是你这样看不到。原因如下。
您的xterm
可执行权限已S_ISGID
设置 (set-group-ID) 位,并且是组拥有的utmp
。
它以这种方式设置,以便xterm
可以将条目添加到/var/run/utmp
和(确切的路径可能会根据您的系统而有所不同),以便您的会话显示在或/var/log/wtmp
的输出中。who
last
有了这些权限,当xterm
执行时,执行它的进程将看到它的有效的组 ID 更改为该utmp
组的 ID(同时读组 ID 将保持不变),这将授予其以写入模式打开utmp
/登录记录的权限。wtmp
在 Linux 上,作为一种安全措施,只能root
列出有效用户 ID 与真实用户 ID 不同或有效组 ID 与真实组 ID 不同的进程的打开文件。 (您会注意到,与其他进程相比,此类进程/proc/<pid>fd
具有权限)。dr-x------ root root
dr-x------ you your-group
这就是为什么lsof
,当以普通用户身份运行时无法列出该xterm
进程的打开文件。你需要运行lsof
为root
.
至于为什么它适用于gnome-terminals
,有几种可能性:
gnome-terminal
不在登录记录中添加条目(我的系统就是这种情况)gnome-terminal
使用utempter
帮手(在这种情况下是 sgidutmp
)添加登录记录。这就是我的系统上xterm
要做的事情konsole
。gnome-terminal
utmp
更新登录记录后(这xterm
不会执行),将有效用户 ID 重置为真实用户 ID(暂时放弃特殊访问权限)。
答案2
这就是伪终端主设备Linux。但xterm使用POSIX函数打开伪终端,隐藏了打开设备的细节。
伪终端有不同的配置,但您的系统可能使用这块:
#elif defined(HAVE_POSIX_OPENPT) && defined(HAVE_PTSNAME) && defined(HAVE_GRANTPT_PTY_ISATTY)
if ((*pty = posix_openpt(O_RDWR)) >= 0) {
char *name = ptsname(*pty);
if (name != 0) {
strcpy(ttydev, name);
result = 0;
}
}
VTE(实际的终端模拟器:“gnome-terminal”是一个正面)使用类似的东西(参见src/pty.cc)。
实际中没有必要继续使用主设备的文件描述符。 xterm 作为两个进程运行,并且用途该文件描述符位于其“父”进程中。它丢弃主设备的文件描述符“子”进程(参见来源)。
当您运行 xterm 时,子进程是你的 shell 与之对话的那个,例如,如果你运行tty
查看您正在使用哪个终端(即使用奴隶伪终端的一侧,以及掌握side 是封闭的,因为每个进程只需要使用伪终端的一侧)。
这父进程(已/dev/ptmx
打开)管理 X 窗口显示。
考虑到所有这些,我希望看到lsof
show xterm 已经/dev/ptmx
打开。除了:
- 在您的屏幕截图中,该消息暗示您没有运行根,如果存在权限问题导致
lsof
其无法查看所有进程,那么这可能是丢失信息的原因。 - 你的 xterm 实际上并没有在你正在运行的机器上运行
lsof
,例如,如果你已经通过 ssh 进入了机器(并且你碰巧看到gnome-terminal
在不同的会话中运行)。