X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/blobdiff_plain/2137669fc54b364d20ae4debaef1744d55acce2c..4251386bc4f6b572a0660c6a8cb56545e30d1cbc:/doc/gtut-tour-11-explicitwait.doc diff --git a/doc/gtut-tour-11-explicitwait.doc b/doc/gtut-tour-11-explicitwait.doc index e8f3fe3d01..37dade0d33 100644 --- a/doc/gtut-tour-11-explicitwait.doc +++ b/doc/gtut-tour-11-explicitwait.doc @@ -1,18 +1,144 @@ /** -@page GRAS_tut_tour_explicitwait Lesson 11: Explicitely waiting for messages (TODO) +@page GRAS_tut_tour_explicitwait Lesson 11: Explicitely waiting for messages \section GRAS_tut_tour_explicitwait_toc Table of Contents - \ref GRAS_tut_tour_explicitwait_intro - \ref GRAS_tut_tour_explicitwait_use + - \ref GRAS_tut_tour_explicitwait_algo + - \ref GRAS_tut_tour_explicitwait_code + - \ref GRAS_tut_tour_explicitwait_code_msg + - \ref GRAS_tut_tour_explicitwait_code_cb + - \ref GRAS_tut_tour_explicitwait_code_api + - \ref GRAS_tut_tour_explicitwait_code_smain + - \ref GRAS_tut_tour_explicitwait_code_cmain - \ref GRAS_tut_tour_explicitwait_recap
\section GRAS_tut_tour_explicitwait_intro Introduction +The messaging primitive we have seen so far are somehow limited on the +receiver side. You have to attach a callback to a message type, and then go +into an infinite loop. Sometimes, you want to block your execution until a +message of a given type arrives. This often occures when you want to deal +with synchronization problems. -\section GRAS_tut_tour_explicitwait_use Defining structure containing explicitwait +As an example, we will study a simple centralized algorithm for mutual +exclusion. In short, when the client wants to enter the critical section +(CS), it sends a specific message to the server, and waits for the server to +answer back with another message. While the client is "locked" waiting for +the message, nothing else should occure for it (no callback or timer should +be served). +The simplest interface to explicit message waiting allows you to specify the +message type you are willing to accept (using gras_msg_wait()). But you can +also specify a list of accepted message types (using gras_msg_wait_or()), or +even provide your own message filters to decide precisly the kind of message +you are waiting for (for example depending on message content -- this is +done using gras_msg_wait_ext()). + +Any message received not matching your expectation will be queued for +further use. Ie, they will be stored in memory and are candidates for the +next gras_msg_handle() or gras_msg_wait(). + +\section GRAS_tut_tour_explicitwait_use Example: mutual exclusion with centralized coordinator + +\subsection GRAS_tut_tour_explicitwait_algo GRAS modelization of the algorithm + +This section naturally provides an example of how to use gras_msg_wait(), +but it can also be seen as an example of the guidelines provided in +\ref GRAS_howto_design. + +So, here are the caracteristics of our example: + +There is two types of processes: + - several clients which want to enter a critical section + - a server, which grants clients to enter the CS when no other + process is already in it. + +There is three kind of messages in the system: + - request (from clients to server) to ask for the permission to enter the CS + - release (from clients to server) to express that they exited the CS + - grant (from server to clients) to allow the given process to enter the CS + +The server has 2 callbacks attached: + - When it gets a request, it checks whether their is already a process in + the CS. If yes, it adds the requester into a FIFO list. If not, it sends + a grant message to the asking client. + - When it gets a release, it checks whether there is some waiting + processes in the waiting queue. If yes, it dequeues the first one and + send a grant message to it. If no, it notes that the CS is free. + +The server has two private data (for the callbacks to work): + - a boolean indicating whether there is a process in the CS already + - a waiting queue (#xbt_dynar_t is quite natural to code this). + +The client interface is composed of two functions: + - lock(), which tries to get the grant from the server to enter the CS. + This is where explicit waiting comes into the game. This function sends a + request to the server, and blocks until the server issues a + grant back. + - unlock(), which informs the server that we exited the CS (by sending a + release message) + +\subsection GRAS_tut_tour_explicitwait_code The code step-by-step + +\subsubsection GRAS_tut_tour_explicitwait_code_msg a) Messages declaration + +First of all, we should have a function declaring all used messages. As said +before, this should be in a separate function so that it can be shared +between all process kinds and avoid code dupplication which may result in +definition discrepency. + +Here, there is no payload attached to the messages. + +\dontinclude 11-explicitwait.c +\skip message_declaration +\until } + +\subsubsection GRAS_tut_tour_explicitwait_code_cb b) Defining private data and callbacks of the server + +Then, we define the callbacks that should be invoqued on the server side +when some messages are received, as previously. For this, we also have to +declare a structure for the private data of the server. + +\skip typedef +\until end_of_release_callback + +\subsubsection GRAS_tut_tour_explicitwait_code_api c) Client-side API + +Now, we define the functions that the client must call to use the service. +Note that this is where the explicit wait feature is used. + +\skip lock +\until end_of_unlock + +\subsubsection GRAS_tut_tour_explicitwait_code_smain d) Server-side initialization + +The core of our distributed service is implemented (protocol, actions on +server side, and accessing function on client side). We should now +initialize the server and let it wait for incomming messages. + +Defining when to stop the server can become tricky. The simplest solution is +to never let the server stop. It simply runs forever. But the simulator will +raise an error at the end, so I won't do so here to keep the output clean. +Another solution would be to deal with client membership properly: clients +registers, use the service and quit afterward. When no client use the +service, the server stops. This would be a bit difficult to implement +(actually, there is an AMOK module to do so simply: \ref AMOK_pm). +Here, we will just hardcode that the clients ask 5 times for the token, and +that there is two clients. This clearly simplify the problem. + +\dontinclude 11-explicitwait.c +\skip gras_userdata_new +\until gras_msg_handle + +\subsubsection GRAS_tut_tour_explicitwait_code_cmain e) Client-side use + +And now, the client is really simple to write: + +\skip message_declaration +\until } \section GRAS_tut_tour_explicitwait_recap Recapping everything together @@ -21,6 +147,6 @@ The program now reads: Which produces the expected output: \include 11-explicitwait.output - + */