Once the user runs the program, we declare and initialize the semaphores of all cooking items, pantry, and the fridges. Upon completion of the initialization of the semaphores we then prompt the user to enter the desired number of bakers they want the program to execute with. Once the number of bakers has been entered we then create that many threads and then the logic for the baking begins.
Once the threads begin the function that gets executed when they get created it starts by beginning a loop through a struct of all the recipes. This struct holds each recipe so that it has a name and then two arrays of booleans that indicate which ingredients it needs to get from both the pantry and the fridge. It then will print out which recipe it has started and will grab all of the ingredients from the pantry and then all of the ingredients required from the fridge. To grab ingredients from each of these spots we utilize helper functions to help readability. In the helper functions it will wait to get into the desired semaphore and then call one other function which takes in a variety of parameters like the task, what baker is calling it, what recipe it is doing, and how long to wait to simulate doing the task. After taking these parameters it will print out the task and sleep for whatever time it was given to simulate the task.
Once all of the ingredients for the current recipe have been grabbed from the pantry and the fridge, the baker will then wait to acquire a bowl, spoon, and a mixer. Once these are free we will access them and then simulate mixing using the doTask helper function. Once we sleep to simulate the task, we then release the cooking tools, and wait for an oven to be free and simulate the time it takes with the doTask function again. Once baking is completed we release the oven and then print that it has finished the recipe; however, there is a chance to be ramsied after completing a recipe forcing the baker to start that recipe over. If this does not occur then the baker moves to the next recipe and repeats the process.
The program will continue until each baker has completed every recipe. Once every baker is done we release the threads, destroy all of the semaphores, and print the bakers have all finished and exit the program.