xcode创build像windows一样的命令行窗口

我有一个Windows应用程序,我将它移植到GLFW的Mac。 在Win32中,我通过::AllocConsole();创build一个cmd窗口::AllocConsole(); 。 我用它来debugging我的脚本。 但在Mac中,似乎没有办法从正在运行的进程创build一个cmd窗口。 lldb适合C ++部分,但对我的python脚本部分没有帮助。 我试图创build一个GLFW窗口来伪造这个,但是GLFW只能运行一个实例,如果我挂断了我的应用,所有的窗口都会暂停。 所以,我正在寻找一种方法来创build从我的应用程序在一个子线程的窗口,它可以作为debugging工具与我的应用程序进行交互。

感谢您的出色问题。 我花了一点时间才弄出一些能在任何类Unix系统上工作的东西。

这是一个起点。 我会把它留给其他人来完善它。

要点:

  • 把过程分成主程序和子程序。

  • 主程序将unix域套接字iostream连接到其选择的unix套接字名称。

  • 子进程产生了一个xterm进程,它使用一个特殊的命令行选项运行相同的程序,给它一个unix域套接字的名字。

  • 在xterm下运行的程序的产生版本监听unix套接字并重复接收到的所有数据(在xterm窗口中)。

  • 原始程序现在可以将数据记录到unix域io_stream中以发出调试数据。

这个程序也应该在cygwin的windows下工作。

 #include <iostream> #include <memory> #include <chrono> #include <system_error> #include <thread> #include <stdlib.h> #include <unistd.h> #include <boost/asio.hpp> using namespace std; namespace asio = boost::asio; asio::io_service io_service; asio::local::stream_protocol::iostream log_stream; int run_program(int argc, char** argv) { for (int i = 0 ; i < 100 ; ++i) { cout << "logging first" << endl; log_stream << i << " hello" << endl; cout << "logged" << endl; this_thread::sleep_for(chrono::milliseconds(400)); } return 0; } auto main(int argc, char** argv) -> int { if (argc == 3 && strcmp(argv[1], "--repeat") == 0) { auto socket_name = string(argv[2]); cout << "listening on " << socket_name << endl; ::unlink(socket_name.c_str()); // Remove previous binding. asio::local::stream_protocol::endpoint ep(socket_name); asio::local::stream_protocol::acceptor acceptor(io_service, ep); asio::local::stream_protocol::socket socket(io_service); acceptor.accept(socket); cout << "accepted" << endl; while (1) { char buf[100]; auto bytes_read = socket.read_some(asio::buffer(buf)); if (bytes_read > 0) { cout.write(buf, bytes_read); cout.flush(); } else { socket.close(); exit(0); } } } else { const auto socket_name = "/tmp/foo"s; cout << "forking" << endl; auto client_pid = fork(); if (client_pid == 0) { cout << "in client" << endl; ostringstream ss; ss << "xterm -e " << argv[0] << " --repeat " << socket_name; auto s = ss.str(); auto err = system(s.c_str()); if (err) { throw system_error(errno, system_category(), "logger child execution"); } } else if (client_pid == -1) { throw system_error(errno, system_category(), "forking"); } else { cout << "pause to allow xterm client to start" << endl; this_thread::sleep_for(chrono::seconds(2)); cout << "making endpoint " << socket_name << endl; asio::local::stream_protocol::endpoint endpoint(socket_name); cout << "connecting to " << endpoint << endl; log_stream.connect(endpoint); cout << "connected" << endl; auto ret = run_program(argc, argv); log_stream.close(); exit(ret); } } return 0; }