Advertisement
Guest User

Untitled

a guest
Nov 20th, 2019
151
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 9.55 KB | None | 0 0
  1. # IPC Problem
  2.  
  3. Inter-process communications where we solve the sleeping barber problem and learn to use and create semaphores.
  4.  
  5. ## Sleeping Stylist with Semaphores
  6.  
  7. The goal of this problem is to solve an inter-thread communication problem called Sleeping Stylist using semaphores. There are 120 customers but only 1 stylist in a hair salon. In the salon, there are 7 chairs that customers can sit and wait for the stylist. Since there is only one stylist, only one customer can get a haircut at a time. If there are no customers in the salon, the stylist sleeps. When a customer enters the salon, the customer wakes up the stylist and then waits for the stylist to get ready. The stylist then takes the customer. If the stylist is busy with a customer and more customers arrive, they sit and wait in the 7 waiting chairs. If a customer enters the salon and it is full (there are already 7 waiting customers while a customer is getting a haircut), the customer leaves to go shopping and then comes back later to try to get a haircut again. **Every customer must eventually get a haircut (no starvation).** When the stylist finishes with a customer, she takes the next waiting customer. If there are no waiting customers, the stylist goes back to sleep. The pseudo-code is given below. **Note that the pseudo-code only suggests a guideline. Feel free to add more parameters, variables, and functions as you think necessary.**
  8.  
  9. You will use the `pthread` package to create 120 customer threads and 1 stylist thread. The program will be called "`sleepingStylistSem.c`". Use a delay loop to slow down each thread (see the pseudo-code) by adjusting the loop bound so that you get a steady stream of customers to compete to get haircuts by the stylist. You want to ensure that your program can demonstrate its operation when the salon is empty, not full and when the salon is full. Also make sure that we can see the gradual build up of customers waiting in the chairs.
  10.  
  11. You should think about the necessary debugging information that you can use to verify the correctness of your implementation. For example, what output will show that the number of waiting threads and the corresponding counter is consistent? How can you show how many customers have already got their haircuts and how many are still trying? Remember, you'll need to convince the grader that your implementation follows our specification precisely.
  12.  
  13. ### sleepingStylistSem.c
  14.  
  15. ```c
  16. #define CHAIRS 7
  17. #define DELAY 1000000 //adjust this value
  18.  
  19. semaphore mutex = 1, stylist = 0, customers = 0;
  20. int waiting = 0;
  21.  
  22. void main(void){
  23. // create a specified number of customer threads
  24. // and a stylist thread. Don't forget to join threads
  25. }
  26.  
  27. void stylist(void){
  28. int j;
  29. while(1) {
  30. down(&customers);
  31. down(&mutex);
  32. waiting = waiting - 1;
  33. up(&stylist);
  34. up(&mutex);
  35. for(j = 0; j<DELAY; j++);
  36. //cut hair
  37. }
  38. }
  39.  
  40. void customer(void){
  41. int j;
  42. while(1) {
  43. down(&mutex);
  44. if(waiting < CHAIRS) {
  45. waiting = waiting + 1;
  46. up(&customers);
  47. up(&mutex);
  48. down(&stylist);
  49. break;
  50. }
  51. else {
  52. up(&mutex);
  53. for(j=0; j < DELAY; j++);
  54. //go shopping
  55. }
  56. }
  57. }
  58. ```
  59.  
  60. ## Sleeping Stylist with Monitor
  61.  
  62. The goal of this problem is to create your own monitor to provide synchronization support for the sleeping stylist problem. You will use the pthread package to create 120 customer threads and 1 stylist thread. There are 7 waiting chairs in the salon. You then need to use a semaphore to create your entry queue. **You also need to create your own Condition Variables (CVs). That is, you CANNOT USE the CV type provided by the pthread library (e.g., `pthread_cond_init`).**
  63.  
  64. If you use pthread CV, you will get 0 for this part. Condition variables are used to suspend processes or threads that cannot continue executing due to a specific monitor state (e.g. the stylist is busy). They are also used to awaken suspended processes or threads when the conditions are satisfiable. To create your own CVs, follow the following steps:
  65.  
  66. 1. You will create a new variable type called `CV`. To do this, you will create a new structure called `cond`. The structure consists of an integer variable that indicates the number of threads blocked on a condition variable and a *semaphore* used to suspend threads. **Your implementation must follow the *signal-and-wait* discipline.** There are three operations that your CV will support. They are:
  67. 1. `count(cv)` -- returns the number of threads blocked on the cv.
  68. 2. `wait(cv)` -- relinquishes exclusive access to the monitor and then suspends the executing threads.
  69. 3. `signal(cv)` -- unblocks one thread suspended at the head of the cv blocking queue. The signaled thread **resumes execution where it was last suspended.** The signaler *exits the monitor and suspends itself at the entry queue.*
  70.  
  71. * You should pay special attention to the following questions during your implementation:
  72. 1. How would you guarantee that only one thread is inside the monitor at one time?
  73. 2. How would you make sure that a suspended thread (due towait) resumes where it left off?
  74. 3. How would you initialize the necessary data structures to support your monitor and make them visible to all threads?
  75. 4. How would you produce the necessary debugging information, in addition to the required information in mon debug Print, that you can use to verify the correctness of your implementation? For example, what kind of output will show that your implementation follows the signal-and-wait discipline and not signal-and-continue? How can you show that the number of waiting threads and the corresponding counter is consistent?
  76.  
  77. 2. You will create function `mon_checkCustomer` that manages the waiting list and takes a customer to the styling chair. It first invokes signal on condition variable `stylistAvailable` to indicate that the stylist is not busy. If the salon is empty, it then invokes wait on the condition variable `customerAvailable` to put the stylist to sleep.
  78.  
  79. 3. You will create function `mon_checkStylist` that puts a customer on the 7 waiting chairs if the salon is not full. If the stylist is sleeping or busy, it first invokes wait on the condition variable `stylistAvailable`. It also invokes signal on condition variable `customerAvailable` to indicate that a customer is waiting.
  80.  
  81. 4. You will create function `mon_debugPrint` to expose internal states of the monitor to help with debugging. The specific format of this function is provided in the pseudo-code in Figure 3.
  82.  
  83. 5. You will create functions `customer` and `stylist`.
  84.  
  85. 6. Make sure that your program produces an output that clearly shows that it follows the **signal-and-wait discipline**. As an example, this can be done via a simple output statement that shows where each blocked thread resumes its execution to after it is awaken from the a queue.
  86.  
  87. ```c
  88. // ==== sleepingStylistMon.c ====//
  89. #define DELAY 1000000 // adjust this value
  90.  
  91. int main (void){
  92. // create specified number of customer threads
  93. // and a stylist thread. Don't forget to join threads
  94. }
  95.  
  96. void stylist(void){
  97. // add more variables as needed
  98. int j;
  99. while(1){
  100. mon_debugPrint();
  101. mon_checkCustomer();
  102. for(j=0; j<DELAY; j++);
  103. // cut hair
  104. }
  105. }
  106.  
  107. void customer(void){
  108. // add more variables as needed
  109. int j;
  110. while(1){
  111. mon_debugPrint();
  112. if(mon_checkStylist())
  113. break;
  114. for(j=0; j<DELAY; j++);
  115. // go shopping
  116. }
  117. }
  118. ```
  119. Figure 2: Pseudo-code for sleeping stylist problem using a monitor
  120.  
  121. ```c
  122. // ===== monitor.c ===== //
  123. #define CHAIR 7
  124. cond stylistAvailable, customerAvailable;
  125. int customer = 0;
  126. int stylist = 0;
  127.  
  128. //add more variables as necessary (e.g. a semaphore for entry queue)
  129.  
  130. void mon_checkCustomer(){
  131. stylist++;
  132.  
  133. signal(stylistAvailabe); // stylist's ready to cut hair
  134.  
  135. //do not use while here
  136. if (customer == 0)
  137. wait(customerAvailable);
  138.  
  139. customer--;
  140. }
  141.  
  142. int mon_checkStylist() {
  143. // This function may have faults.
  144. // If you think it does, you'll need to fix it
  145.  
  146. int status = 0;
  147.  
  148. if(customer < CHAIRS){
  149. customer++;
  150.  
  151. signal(customerAvailable);
  152.  
  153. if(stylist == 0) // do not use while here
  154. wait(stylistAvailable);
  155.  
  156. stylist--;
  157.  
  158. status = 1;
  159. }
  160. return status;
  161. }
  162.  
  163. /**
  164. * Print how many customers are waiting
  165. */
  166. void mon_debugPrint(void){
  167. /** print the state of the waiting char using the following format
  168. * (the following four lines are the sample output):
  169. * |1|1|1|0|0|0|0| => 3
  170. * Given haircuts = X
  171. * Salon full = Y times
  172. * Salon empty = Z times
  173. *
  174. * Below is the explanation of each line.
  175. *
  176. * Line 1: For each slot, - indicates that the chair is available
  177. * and 1 indicates that the chair is occupied.
  178. *
  179. * The value after => indicates the number of occupied chairs.
  180. *
  181. * Line 2: X = number of completed haircuts.
  182. *
  183. * Line 3: Y = number of times that all waiting chairs are full.
  184. * That is, each time the number of occupied chairs increases to 7,
  185. * this counter should go up by 7.
  186. *
  187. * Line 4: Z = the number of times that the stylist goes to sleep.
  188. * That is, each time the stylist goes to sleep, this counter should
  189. * go up by 1.
  190. */
  191. }
  192. ```
  193. Figure 3: Pseudo-code of the monitor functions
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement