NCurses 不恢复终端行为

NCurses not restoring terminal behavior

亲爱的 Communauts,您好,

我正在为我正在开发的并行软件创建一个终端动画状态报告。我正在使用 NCurses。 我遇到了与恢复终端标准行为相关的问题。 在 运行 我的软件之后,无论我是否调用 endwin() ,终端都只有 24 行。 这里是简化代码:

int size=10;
initscr();
refresh();
while(KeepAlive){
      int j=1;
      mvprintw(j,0,/*Blah blah header*/));
      for(int i=0;i<size;i++){
          j++;  
          mvprintw(j,0,/*Some blah blah*/);
       }
       refresh();
       usleep(1000000);
}
endwin();

KeepAlive是另一个线程改变的控制变量(所以while不是无限循环,而是受控循环)。 在 运行 这个软件之后我的终端只有 24 行,echo 工作,但是有很多空白 space.

非常感谢您的帮助,玩得开心

编辑:

我想与您分享我在尝试解决我的问题时发现的一些信息:

  1. curses (ncurses) 在 openMP 下完美运行,然后您可以想象一些线程执行您的数学计算和一个线程(只有一个,请注意)给出一些运行时信息。
  2. curse (ncurses) 与 MPI 不兼容。嗯,正确的说法是“不完全”与 MPI 兼容。 MPI 非常复杂 stdin/stdout/stderr,因为所有 MPI 进程的所有输出都可以重定向到显示器(可以指定)。使用任何高级终端输出覆盖库都会导致代码错误或意外行为。

MPI 常见问题解答支持:

Maybe. But probably not.

Open MPI provides fairly sophisticated stdin / stdout / stderr forwarding. >However, it does not work well with curses, ncurses, readline, or other >sophisticated I/O packages that generally require direct control of the terminal.

Every application and I/O library is different -- you should try to see if yours >is supported. But chances are that it won't work.

Sorry. :-(

找到 here (MPI reference)

我发现即使你只指定一个 MPI 进程来管理所有的 curses 输出(只是那个进程在开始时调用 initscr() 并在他那部分代码的末尾调用 endwin() ) 无法强制 curses 使用完整的终端(只有默认的 UNIX 24x80 可用)。 MPI 完成后,您的整个终端将继续以 24x80 模式工作,直到调用重置。

感谢所有帮助过我的社区,

玩得开心

女友

应该可以。关于 "parallel" 的评论建议使用多线程,这可能意味着您的输出没有像预期的那样刷新。

这可能是同一个问题 (Ncurses limited output size),为此提供了更多信息。这两个问题都没有提供足够的细节来提供比通用建议更多的内容。

一种可能的解决方案是将您的文本 GUI 与其余 MPI 代码完全分离,并使这两个部分通过 MPI-2 的 client/server 机制相互通信。这意味着:

  1. 运行 作为单例 MPI 程序的 GUI,即调用 MPI_Init{_thread} 但不是通过 mpiexec 启动的程序。然后它应该通过调用 MPI_Open_port 打开一个监听端口。调用 returns 必须提供给应用程序计算部分的字符串端口名称。然后 GUI 部分应该通过调用阻塞 MPI_Comm_accept.

  2. 开始监听连接
  3. 计算部分通过 mpiexec 照常启动。它应该通过调用 MPI_Comm_connect 给定来自 (1) 的端口名称来连接到 GUI。

  4. GUI 中的 MPI_Comm_accept 和计算部分中的 MPI_Comm_connect 的组合建立了一个内部通信器,可用于在两个部分之间发送消息。计算部分可以例如定期向 GUI 发送状态消息。如有必要,内部通信器可以进一步 "flattened" 到内部通信器。

  5. 一旦计算完成,通信部分应通过调用MPI_Comm_disconnect断开连接。

  6. GUI 应该调用 MPI_Close_port 并完成它自己的执行。

在那种情况下,GUI 部分可以是本地或通过 SSH 远程启动的文本模式 curses 应用程序、X11 GUI 应用程序或其他任何东西。