Skip to content

Instantly share code, notes, and snippets.

@GaretJax
Created May 13, 2010 18:28
Show Gist options
  • Save GaretJax/400189 to your computer and use it in GitHub Desktop.
Save GaretJax/400189 to your computer and use it in GitHub Desktop.
private process TicketShop {
// Wait to receive the array containing the references to all cars
receive this.cars(this.cars);
// Light sanity check to ensure that we have a valid cars array
// NOTE: We don't test for null values here and the whole array is
// passed by reference (are we sure? How behaves JR when passing
// values around using messages between multiple virtual machines?)
assert this.cars != null && this.cars.length > 0;
// Wait until the park is open
receive this.open();
out("The roller coaster is now open!");
int prev = this.cars.length - 1; // The index of the previous car
// Send to each car a message containing his ID and the car which comes
// before it on the ramp.
//
// The previous car is then used to synchronize the cars queue and to
// avoid overtakings along the ride.
for (int i = 0; i<this.cars.length; i++) {
send this.cars[i].prevCar(i, prev, this.cars[prev]);
prev = (prev + 1) % this.cars.length;
}
// Notify the first car in the queue that the roller coaster is now open
send this.cars[this.cars.length-1].ready();
// The name of the last registered passenger (used only for the output)
String name;
// This loops runs until it blocks because a part of passengers has already
// finished their iterations and the remaining passengers are not enough to
// fill up a car. This causes a deadlock which is detected by the JR
// runtime, causing it to execute the registered quiescence action.
//
// This function will do one more iteration and then the JR park will
// definitively close.
while (!this.stopped) {
out("Waiting for the next car");
int id; // The id of the next free car
int capacity; // The capacity of the next free car
// The callback used to send the "ride start" message
cap void (remote Passenger[]) start;
// The seats of the passengers of this car
remote Passenger[] passengers = new remote Passenger[capacity];
// Wait for the next free car
receive nextCar(start, id, capacity);
out("Car %d is now ready, load %d passengers!", id, capacity);
// Collect tickets
for (int i = 0; i < capacity; i++) {
// Wait for a passenger
receive nextPassenger(name, passengers[i]);
// If the last passenger was null, then shorten the array to hold
// only non null values and start the car with only the passengers
// currently in the array.
// This happens only when the quiescence action sends a nextPassenger
// message holding null values to start the last ride.
if (passengers[i] == null) {
assert this.stopped; // We start the last tour with an incomplete
// car only if the park is already closed.
// Temporary array to shorten the current one
remote Passenger[] temp = passengers;
passengers = new remote Passenger[i];
System.arraycopy(temp, 0, passengers, 0, i);
// Stop waiting for others passengers, they will never arrive.
break;
}
// Let the passenger take his place
out("%s (%d/%d) is sitting down", name, i + 1, capacity);
}
if (passengers.length > 0) { // Start the ride only if there is at least
// one passenger.
if (passengers.length == capacity) { // The car is full
out("Car %d is now full, start it!", id);
} else {
out("Starting car %d with %d out of %d passengers.", id, passengers.length, capacity);
}
// Start the car
send start(passengers);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment