Question

How to execute xterm from XWindow program, insert it into my window, but continue execution both while xterm is active and after it was closed?

In my XWindows (XLib over XCB) application I want to execute xterm -Into <handle>. So that my window contains xterm window in it. Unfortunately something wrong is happening.

pseudo code:

if (fork() == 0) {
    pipe = popen('xterm -Into ' + handle);
    while (feof(pipe)) gets(pipe);
    exit(0);
}

I tired system() and execvp() as well. Every thing is fine until I exit from bash that runs in xterm, then my program exits. I guess that connection to X server is lost because it is shared between parent and child.

UPDATE: here is what is shown on terminal after program exits (or rather crashes).

XIO:  fatal IO error 11 (Resource temporarily unavailable) on X server ":0.0"
   after 59 requests (59 known processed) with 1 events remaining.
[xcb] Unknown sequence number while processing queue
[xcb] Most likely this is a multi-threaded client and XInitThreads has not been called
[xcb] Aborting, sorry about that.
y: ../../src/xcb_io.c:274: poll_for_event: Assertion `!xcb_xlib_threads_sequence_lost' failed.
Aborted

No correct solution

OTHER TIPS

One possibility is that you are terminating due to the SIGCHLD signal not being ignored and causing your program to abort.

    signal(SIGCHLD, SIG_IGN);

Another is, as you suspect something actively closing the X session. Just closing the socket itself should not matter but are you using a library that registers an atexit call it could cause an issue.

Since from your snippet, it looks like you don't actually care about the stdout of the xterm, a better way to do it would be to actuall close fd's 0,1,2. Also since it looks like you don't need to do anything in the child process after xterm terminates you can use 'exec' rather than 'popen' to fully replace the child process with that of the xterm including any cleanup handlers that were left around. Though, I am not sure how pruned your snippet is from what you want to do as obviously the call to 'gets' is not what you want.

to make sure the X connection is closed, you can set its close on exec flag with the following. (this will work on POSIX systems where the x connection number is the fd of the server socket)

 fcntl(XConnectionNumber(display), F_SETFD, fcntl(XConnectionNumber(display), F_GETFD) | FD_CLOEXEC);

Also note that 'popen' itself forks in the background in addition to your fork, I think you probably want to do an execvp there then use waitpid(... , WNOHANG) to check for the childs termination in your main X11 loop if you care to know when it exited.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top