//------------------------------------------------------------------- // msgserver.cpp // // This example uses the 'recvmsg()' and 'sendmsg()' functions // to accept a message from a client and then to echo it back. // The user may terminate this program by hitting -C. // // to compile: $ g++ msgserver.cpp -o msgserver // to execute: $ ./msgserver // // programmer: ALLAN CRUSE // written on: 24 JAN 2009 // revised on: 15 FEB 2009 -- to return same length as received //------------------------------------------------------------------- #include // for printf(), perror() #include // for exit() #include // for bzero() #include // for gethostname() #include // for inet_ntoa() #define SERVER_PORT 54321 int main( int argc, char **argv ) { //----------------------------------------------- // get this station's hostname for later display //----------------------------------------------- char hostname[ 64 ] = {0}; gethostname( hostname, 63 ); //------------------------------------------------------------------ // create an internet datagram socket to receive incomming messages //------------------------------------------------------------------ int sock = socket( AF_INET, SOCK_DGRAM, IPPROTO_IP ); if ( sock < 0 ) { perror( "socket" ); exit(1); } //--------------------------------------------------------- // set a socket-option allowing this socket to be reusable //--------------------------------------------------------- int oval = 1; int olen = sizeof( oval ); if ( setsockopt( sock, SOL_SOCKET, SO_REUSEADDR, &oval, olen ) < 0 ) { perror( "setsockopt" ); exit(1); } //------------------------------------------------------------------ // initialize a socket-address structure using a 'wildcard' address //------------------------------------------------------------------ struct sockaddr_in saddr; socklen_t salen = sizeof( saddr ); bzero( &saddr, salen ); saddr.sin_family = AF_INET; saddr.sin_port = htons( SERVER_PORT ); saddr.sin_addr.s_addr = htonl( INADDR_ANY ); //-------------------------------------------------- // bind the socket to this socket-address structure //-------------------------------------------------- if ( bind( sock, (sockaddr*)&saddr, salen ) < 0 ) { perror( "bind" ); exit(1); } //------------------------------------------ // main loop to receive connection-requests //------------------------------------------ int count = 0; do { // setup structures needed in our 'struct msghdr' object struct sockaddr_in from; socklen_t flen = sizeof( from ); bzero( &from, flen ); char buf[ 1500 ] = {0}; int blen = sizeof( buf ); struct iovec myiov[ 1 ] = { { buf, blen } }; // allocate and initialize the 'struct msghdr' object struct msghdr mymsg; size_t msglen = sizeof( mymsg ); bzero( &mymsg, msglen ); mymsg.msg_name = &from; mymsg.msg_namelen = flen; mymsg.msg_iov = myiov; mymsg.msg_iovlen = 1; mymsg.msg_control = NULL; mymsg.msg_controllen = 0; mymsg.msg_flags = 0; // show the socket's port-number and the name of this host printf( "\n ok, server is listening" ); printf( " to port %u on %s ... ", SERVER_PORT, hostname ); fflush( stdout ); // receive a client's message sent to this server's port int rx = recvmsg( sock, &mymsg, 0 ); if ( rx < 0 ) { perror( "recvmsg" ); exit(1); } printf( "\n #%d received %d bytes ", ++count, rx ); printf( "from \'%s\' \n\n", inet_ntoa( from.sin_addr ) ); puts( buf ); // send the received message back to its client myiov[0].iov_len = rx; int tx = sendmsg( sock, &mymsg, 0 ); if ( tx < 0 ) { perror( "sendmsg" ); exit(1); } printf( "\n returned %d bytes ", tx ); printf( "to \'%s\' \n\n", inet_ntoa( from.sin_addr ) ); } while ( 1 ); }