free_bookz_player
by using a central repository. You have been
hired to implement the necessary changes/additions.
adz_server
must be multi-threaded. Specifically, each request must be
handled in its own thread.
adz_server
must use one exogenous,
circular, single-linked data structure to hold the repository in
memory. (Note: This structure will be shared by the threads that
handle the requests.)
free_bookz_player
must accept a second command-line argument containing the IP address
of the adz_server
. If no such argument is provided,
it must use 127.0.0.1 as the default. (Note: There is no need to
error-check the argument since it will only be provided by
qualified testers.)
When the node contains the data itself it is said to be an endogenous structure and when the node contains a pointer to the data it is said to be an exogenous structure.
When the node contains only one pointer to another node (either the next node in the structure or the previous node in the structure) it is said to be single-linked. On the other hand, when the node contains a pointer to both the next node in the structure and the previous node in the structure it is said to be doubly-linked.
Finally, when the "last" node in the structure points
to NULL
it is said to be a linear structure
and when the "last" node in the structure points to the "first"
node in the structure, it is said to be a circular
structure.
So, the structure that you must use for this assignment can be visualized as follows.
adz
, which consists of
both a delay and text. So, it can be encapsulated as follows.
struct adz { int delay; char text[38]; };
The elegant way to encapsulate a node is to use a void
*
so that it can be used with any kind of data (though a
typecast will be required). This might be done as follows.
struct node { void *data; struct node *next; };
The less elegant approach is to create a node structure that is appropriate
only for use with an adz
.
struct adz_node { struct adz *data; struct adz_node *next; };
adz
you will want to:
adz
).To that end, when populating the structure, you will want to have a pointer to the "first" node and a pointer to the "last" node.
Initially, the "current" node must be the "first" node. Then, as you move through the structure the "current" node will become the "current's next" node.
However, since the request-handler threads all must use the data structure, the operations/variables associated with iterating over the structure must be thread-safe.
adz_lib
currently reads adz
information from
the local file system (probably in a while()
loop that
makes use of keep_going
in its condition).
For this version it must instead send a request to the adz_serve
.
Fortunately, since read()
is already being called in a
helper thread, the additional latency won't have any deleterious
impacts on the display of the
bookz
.
(Note: It would have been better if we had included a get_adz()
function in the original design that called read()
. Then,
the only function we would need to change in this version would be
get_adz()
.)
sleep()
) in an effort to identify any race
conditions.
free_bookz_player
and the server (i.e.,
the adz_server
). When you've completed both and begin
testing you should:
repository.adz
and one of the
earlier adz
files.
sleep()
to ensure that
it is handling multiple connections simultaneously.)
adz_server
dynamically allocates memory (for the
linked structure) and, so, should deallocate that memory at some point.
Unfortunately, to keep the server as simple as possible, it does not
terminate normally (i.e., it must be interrupted from the keyboard using
Ctrl+C).
You might think that you could change the disposition of SIGINT
and deallocate memory in the handler. However, the disposition of
SIGINT
can't be changed (to ensure that processes can always
be interrupted).
You might also think that you could register an exit handler using
atexit()
. However, exit handlers are only invoke when a
process terminates normally.
makefile
) needed to build both
the free_bookz_player
and the adz_server
.
Though you must keep an "old" version of the adz_lib
module, you do not need be able to build both v2 and v3 of
the free_bookz_player
from the same source code. (You
should, however, understand why it would be beneficial to be able to
do so and how you would do so.)
Copyright 2017