ou.cc
and om.cc
. Unless you decide to have
more than one source file for each program, the Makefile for this
project may consist of just the following two lines:
LDLIBS = -lsocket -lnsl all : ou omMake automatically adds the
LDLIBS
macro to the g++
command any time it uses an implicit rule to invoke the linker
(ld), just as it adds the CXXFLAGS
that you already
know about. The two libraries named in this macro are needed for any
programs that use sockets. However, if you build your programs on
qcunix1 you have to omit the nsl
library because
they don't use it and it isn't available there.If you use the strtok_r() function in either of your programs, you will also have to modify the value of CXXFLAGS in your Makefile:
CXXFLAGS = -g -Wall -D_REENTRANTThe two programs will communicate by exchanging datagrams. Since you have sample code for stream sockets, but not for datagram sockets, here are the changes you will have to make to use datagrams:
SOCK_DGRAM
instead of SOCK_STREAM
.
bytesReceived = recvfrom( well_known_socket_fd, buffer_to_receive_datagram, sizeof buffer_to_receive_datagram, 0, // Flags: none need to be set. &sockaddr_for_sender, &sockaddr_for_sender_size);When a datagram arrives,
sockaddr_for_sender
will be
filled in with host address and port number for the datagram sender;
and sockaddr_for_sender_size is an int that you must
initialize before each call to recvfrom() with the size of a
sockaddr_in
struct, and which the kernel will modify
with the size of the socket address before the call returns. (This
is for generality so that datagrams could be sent and received using
different formats for the socket addresses on the client and server
ends. We don't use this feature, but we have to make our code
consistent with it anyway.)
bytesSent = sendto( well_known_socket_fd, message_to_send, strlen(message_send), 0, // Flags: none need to be set. &sockaddr_for_sender, sockaddr_for_sender_size);The
sockaddr_for_sender
would be the same struct that
was used in the matching call to recvfrom(). Note that unlike
recvfrom(), the last argument is a value, not a pointer in
this function.
sendto( ... ) alarm(1) br = recvfrom( ... ) if (-1 == br && EINTR == errno) server did not reply within one second
Create a datagram socket and bind it to your assigned well-known port number. When a datagram arrives it will be a request formatted as a text string with spaces as delimiters between tokens. The first token in the datagram is a request type for selecting a function to call to process the request. Pass the remainder of the datagram as a single argument to the appropriate processing function, which is returns a character string. Send that string as a reply to the sender of the request. Use a dispatch table as described in class to match request types with processing functions. If a request has an unrecognized request type, send the string "*** unrecognized request ***" to the sender.
For this use case, om recognizes two request types, and processes them as follows:
Request Type | Argument List | Returns |
---|---|---|
listClasses | Anything | The names of all the classes being mangaged, separated by newlines. |
exit | Anything | Nothing. Print the argument list, and exit om. |
install_doc : ou.1 om.1 <tab>cp -f ou.1 om.1 $(HOME)/man/man1
$Id$
keyword
in it. Make sure there is a comment line with the $Log$
keyword in it in each of these files.Add the following rule to your Makefile:
install : install_doc ou om <tab>cp -f ou om $(HOME)/bin <tab>chmod 755 $(HOME)/bin/ou $(HOME)/bin/omNote: Your executable programs must be named ou and om. Your source files may be named whatever you like, but when you pick the names, remember that their names will not change for different use cases. I suggest that you use the names
om.cc
and ou.cc
.Be sure your source code follows the coding guidelines for this course before proceeding. You should have been formatting and documenting your code as you wrote it. Now is the time to proofread everything to make sure it looks right.
Check everything into rcs and be sure "make install" builds and installs everything correctly. Be sure all the rcs keywords are expanded correctly in all the source files. Revise source files, man pages, and the Makefile and check them in again as necessary.
Double check everything. It is difficult to get make and rcs to recreate a use case properly once you start working on the next one.