Hello,

I have written a client/server program using libc 5.3.12
on Linux 2.0.33.  The server program communicates with
the client via socket.  The server executes a python
script ( specified by the client ) in the same process,
and returns the data which have been written to "stdout"
by the script.

Now I'm in trouble because the script executed by the server
can't write large data to "stdout".

Then I have written a simple program ( bottom of this message )
which consists of the part of the server program and a dummy
function ( read_and_write() ) instead of the function executes
a python script.  In addition, this program writes data to
a file instead of sending data to a client.  And I ran it.

If the size of the file "sample.dat" was 65535 bytes and under,
the program terminated with no errors. But the size was over
65535 bytes, the fwrite() call in the read_and_write() failed
and "errno" was set to 512.

        ##### Write error! ERROR No. : 512

Is there any improper part in this program?  Or, is there
any other way to read from "stdout" asynchronously?

I thank you in advance for your advice.


Regards,
Masahiko Shimoda




#include <stdio.h>
#ifdef sun
#include <sys/types.h>
#include <stropts.h>
#endif
#include <sys/socket.h>
#include <fcntl.h>
#include <signal.h>
#include <errno.h>
#include <sys/stat.h>

#define INPUT_FILE      "sample.dat"
#define OUTPUT_FILE     "result.dat"

static void     signal_sigpoll( int signo ) ;
static int      read_and_write( void ) ;


static int       sfd_S[2] ;
static FILE     *ofp_S ;



int     main( int argc, char argv[] )
{
        struct sigaction         act ;


        ofp_S = fopen( OUTPUT_FILE, "w" ) ;
        if( ofp_S == NULL )
        {
            fprintf( stderr, "fopen() error.\n" ) ;
            exit( 1 ) ;
        }

        if( socketpair( AF_UNIX, SOCK_STREAM, 0, sfd_S ) )
        {
            fprintf( stderr, "socketpair() error.\n" ) ;
            exit( 1 ) ;
        }


        if( dup2( sfd_S[1], fileno( stdout ) ) < 0 )
        {
            fprintf( stderr, "dup2() error.\n" ) ;
            exit( 1 ) ;
        }


#ifdef sun
        signal( SIGPOLL, signal_sigpoll ) ;
#else /* linux */
        sigaction( SIGPOLL, NULL, &act ) ;
        act.sa_handler = signal_sigpoll ;
        act.sa_flags = SA_RESTART ;
        sigaddset( &act.sa_mask, SIGPOLL ) ;
        act.sa_restorer = NULL ;
        sigaction( SIGPOLL, &act, NULL ) ;
#endif

#ifdef sun
        ioctl( sfd_S[0], I_SETSIG, S_RDNORM ) ;
        fcntl( sfd_S[0], F_SETFL, O_NDELAY ) ;
#else /* linux */
        fcntl( sfd_S[0], F_SETOWN, getpid() ) ;
        fcntl( sfd_S[0], F_SETFL, FASYNC | O_NDELAY ) ;
#endif


        read_and_write() ;

        fflush( stdout ) ;

        fclose( ofp_S ) ;

        exit( 0 ) ;
}



static void     signal_sigpoll( int signo )
{
        char    buff[BUFSIZ] ;
        int     length ;



#ifdef sun
        sighold( SIGPOLL ) ;
#endif

        length = read( sfd_S[0], buff, BUFSIZ ) ;
        while( length > 0 )
        {
            fwrite( buff, 1, length, ofp_S ) ;
            length = read( sfd_S[0], buff, BUFSIZ ) ;
        }

#ifdef sun
        signal( SIGPOLL, signal_sigpoll ) ;
        sigrelse( SIGPOLL ) ;
#endif

        return ;
}



static int      read_and_write( void )
{
        struct stat      st_buf ;
        FILE            *ifp ;
        char            *buff ;
        size_t           len ;



        if( stat( INPUT_FILE, &st_buf ) )
        {
            fprintf( stderr, "stat() error.\n" ) ;
            return( 1 ) ;
        }

        buff = ( char * )malloc( st_buf.st_size ) ;
        if( buff == NULL )
        {
            fprintf( stderr, "malloc() error.\n" ) ;
            return( 1 ) ;
        }

        ifp = fopen( INPUT_FILE, "r" ) ;
        if( ifp == NULL )
        {
            fprintf( stderr, "fopen() error.\n" ) ;
            return( 1 ) ;
        }

        fread( ( void * )buff, 1, st_buf.st_size, ifp ) ;

        fclose( ifp ) ;

        len = fwrite( ( void * )buff, 1, st_buf.st_size, stdout ) ;

        if( ferror( stdout ) )
        {
            fprintf( stderr, "##### Write error! ERROR No. : %d\n", errno ) ;
            return( 1 ) ;
        }

        return( 0 ) ;
}

-
To unsubscribe from this list: send the line "unsubscribe linux-net" in
the body of a message to [EMAIL PROTECTED]

Reply via email to