在Windows系统中,控制台窗口的所有权是如何工作的?

5
当从另一个控制台应用程序启动控制台应用程序时,控制台所有权是如何工作的?
我看到有四种可能性:
1.第二个应用程序在其生命周期内继承自第一个应用程序的控制台,控制台在退出时返回给原始所有者。 2.每个应用程序都有自己的控制台。然后,Windows以某种方式将两者的内容合并为用户可见的“控制台”。 3.第二个应用程序获得属于第一个应用程序的控制台的句柄。 4.控制台被放置在共享内存中,两个应用程序拥有相等的“所有权”。
很可能我错过了一些东西,这四个选项都不能充分描述Windows对其控制台所做的操作。
如果答案接近选项4。我的后续问题是哪个进程负责管理窗口?(处理需要刷新/重绘屏幕时的图形更新等)
一个具体的例子:运行CMD。然后,使用CMD运行[控制台应用程序]。[控制台应用程序]将写入似乎与CMD使用的相同的控制台窗口。
6个回答

6
你提出的四种可能性都不是事实,并且你后续的问题,“哪个进程负责管理窗口?”的答案是,没有一个进程负责。TUI程序 根本不需要知道窗口的任何信息,在底层,它们甚至不一定与GUI连接在一起。
控制台是对象,通过句柄访问,就像文件、目录、管道、进程和线程一样。单个进程并不通过其对控制台的句柄“拥有”控制台,就像进程“拥有”它打开的任何文件一样。控制台的句柄与所有其他(可继承的)句柄一样,由子进程从它们的父进程继承。你的TUI应用程序由CMD启动,只需继承CMD指定应该继承的标准句柄,当它调用CreateProcess()时 - 这通常会是CMD的标准输入、输出和错误(除非命令行告诉CMD使用其他句柄作为子进程的标准输入、输出和错误)。

控制台并不依赖于CMD。只要存在以下情况之一,即(a) 任何打开的句柄指向控制台的输入或输出缓冲区,或者(b) 有任何其他“附加”到控制台的进程,它们就会存在。因此,在您的示例中,您可以终止CMD,但仅当您终止子进程时,控制台才会被实际销毁。

负责显示GUI窗口的进程,其中呈现控制台的是在Windows NT 6.1之前的版本中,称为客户端-服务器运行时子系统(CSRSS)。窗口处理代码位于WINSRV.DLL中,其中包含“控制台服务器”,Win32程序执行控制台I/O时会对其进行LPC调用。在Windows NT 6.1中,由于Raymond Chen所涵盖的原因, 这种功能从CSRSS移出到CSRSS生成的权限较低的进程中。


1

我的猜测在3到4之间。控制台是一个独立的对象,具有标准输入、输出和错误流。这些流附加到第一个使用控制台的进程上。如果没有重定向(例如运行带有重定向到文件的命令),后续进程也可以继承这些流。

通常情况下不会有争用,因为父进程通常会等待其子进程完成,而异步进程通常会启动自己的控制台(例如在命令提示符中尝试“start cmd”)或重定向标准输出。

然而,没有任何阻止两个进程同时写入输出流的东西 - 这些流是共享的。当使用某些运行时库时,这可能是一个问题,因为对标准输出/错误的写入可能不会立即刷新,导致混杂的输出。一般来说,除非通过并发原语如Mutexes、Events等协调它们的输出,否则要求两个进程主动写入同一个输出流通常不是一个好主意。


1
SDK所描述的方式强烈类似于CreateProcess中的选项之一:CREATE_NEW_CONSOLE。它描述如下:新进程有一个新的控制台,而不是继承其父进程的控制台(默认情况)。有关更多信息,请参见控制台的创建。
输出是通过句柄进行的,您可以使用GetStdHandle()获得一个句柄。传递STD_OUTPUT_HANDLE返回控制台句柄,假设未重定向输出。实际输出是通过WriteFile()或WriteConsole/Output()完成的。如果两个进程都将输出写入处理程序,则它们的输出将随机混合。否则与两个程序写入同一文件句柄时会发生的情况完全相同。
从逻辑上讲,控制台与屏幕缓冲区相关联。您可以使用SetConsoleScreenBufferXxx()进行调整。从那时起,您可以将其称为共享内存。实际实现是不可发现的,处理程序将其抽象化,就像任何Win32 API一样。随着新的conhost.exe进程的到来,它在Vista中肯定已经发生了很大的变化。

0
每个应用程序将在自己的AppDomain中运行。每个AppDomain都应该运行它自己的控制台。
啊,你是对的。我在考虑在进程内运行可执行文件,并忘记它们会启动自己的进程 - 我没有深入研究。

控制台是Windows的概念,它是按进程而非AppDomain进行的。 - user90843

0

CMD“拥有”控制台。当它为应用程序创建进程时,该应用程序继承了对控制台的句柄。它可以读取和写入这些内容。当进程消失时,CMD继续拥有控制台。

注意:我不确定“所有权”是否是这里正确的词语。当CMD退出时,Windows将关闭控制台,但这可能只是一个简单的设置。


0

我认为在文档中已经很清楚地解释了。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接