Re: more pipe questions



Ah yes, you are using gdk_input_add, which does mean non-blocking, which means streams stuff (like fgets()) don't work properly with it.
cleanest to do popen() and fgets() kind of stuff manually, then.

you've hassled us enough for me to play with what you have been trying to do ;)
I have attached the program I've made, it seems to work perfectly, I hope you find it useful :)

> But I get no input anymore in the function lavreclog_input()...I guess I
> need to set it nonblocking/flushing. How do I do that? Or is it something
> else? I thought fcntl, but that didn't work, I think - still no input...
> 
> Ronald
> 
#include <gtk/gtk.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <signal.h>
#include <sys/wait.h>

void follow_lav_log (void);
gint fork_tail (void);
void lavreclog_input_cb (gpointer data, gint source, GdkInputCondition condition);

int studio_lavreclog_cid;
gint studio_lavreclog_gint;

int main (int argc, char *argv[])
{
    GtkWidget *window, *button;

    gtk_init (&argc, &argv);

    window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
    gtk_signal_connect (GTK_OBJECT (window), "destroy",
			GTK_SIGNAL_FUNC (gtk_main_quit), NULL);
    gtk_container_set_border_width (GTK_CONTAINER (window), 5);

    button = gtk_button_new_with_label ("ho ho ho");
    gtk_signal_connect_object (GTK_OBJECT (button), "clicked",
			       GTK_SIGNAL_FUNC (g_print), "ho ho ho\n");	// hehe
    gtk_container_add (GTK_CONTAINER (window), button);
    gtk_widget_show (button);

    follow_lav_log ();

    gtk_widget_show (window);
    gtk_main ();

    return 0;
}

void follow_lav_log (void)
{
    gint fd;

    if ((fd = fork_tail ()) < 0)
    {
	g_print ("tail fork failed, exiting\n");
	return;
    }

    studio_lavreclog_gint = gdk_input_add (fd, GDK_INPUT_READ, lavreclog_input_cb, NULL);
}

gint fork_tail (void)
{
    int mypipe[2];
    char file[100];

    sprintf (file, "%s/%s/%s", getenv ("HOME"), ".studio", "lavrec.log");

    if (pipe (mypipe) < 0)
	return -1;
    
    switch (studio_lavreclog_cid = fork())
    {
	case -1:
	    return -1;
	case 0:
	    close (mypipe[0]);
	    close (1);

	    dup2 (mypipe[1], 1);

	    execlp ("tail", "tail", "-0f", file, NULL);
	    exit (1);
    }

    fcntl (mypipe[0], F_SETFL, O_NONBLOCK);
    close (mypipe[1]);

    return mypipe[0];
}

void lavreclog_input_cb (gpointer data, gint source, GdkInputCondition condition)
{
    char buff[129], *p;
    int ret;

    p = buff;
    do
    {
	ret = read (source, p, 1);
    } while (*p++ != '\n' && ret > 0); // overflowable, I don't care :)

    if (ret <= 0)
    {
	if (p - buff > 1)
	{
	    *p = '\0';
	    g_print ("LAVREC: %s\n", buff);
	}
	g_print ("Lavreclog completed\n");
	close (source);
	gdk_input_remove (studio_lavreclog_gint);
	kill (studio_lavreclog_cid, SIGKILL);
	waitpid (studio_lavreclog_cid, NULL, 0);
	return;
    }

    *(p - 1) = '\0';
    g_print ("LAVREC: %s\n", buff);
}


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]