|
From: <mar...@us...> - 2008-02-15 04:12:54
|
Revision: 103
http://gridsim.svn.sourceforge.net/gridsim/?rev=103&view=rev
Author: marcos_dias
Date: 2008-02-14 20:13:00 -0800 (Thu, 14 Feb 2008)
Log Message:
-----------
Stable version of the multiple queue aggressive backfilling policy.
Modified Paths:
--------------
branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues01.java
branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues02.java
branches/gridsim4.0-branch3/source/gridsim/gui/DefaultGridSimVisualizer.java
branches/gridsim4.0-branch3/source/gridsim/turbo/CBParallelSpaceShared.java
branches/gridsim4.0-branch3/source/gridsim/turbo/MultipleEasyBackfillingQueues.java
branches/gridsim4.0-branch3/source/gridsim/turbo/SSGridlet.java
branches/gridsim4.0-branch3/source/gridsim/turbo/TResourceCharacteristics.java
Added Paths:
-----------
branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePartitionPredicate.java
Removed Paths:
-------------
branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePredicate.java
Modified: branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues01.java
===================================================================
--- branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues01.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues01.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -145,16 +145,9 @@
// this resource will use an aggressive backfilling policy (EASY)
TResourceCharacteristics resConfig = new TResourceCharacteristics(
- arch, os, mList, TResourceCharacteristics.EB_PARALLEL_SPACE_SHARED,
+ arch, os, mList, TResourceCharacteristics.MULTIPLE_EASY_BACKFILLING_QUEUES,
time_zone, cost);
- MultipleEasyBackfillingQueues policy = null;
- try {
- policy = new MultipleEasyBackfillingQueues(name, "Policy", 1);
- } catch (Exception e1) {
- e1.printStackTrace();
- }
-
//////////////////////////////////////////
// 6. Finally, we need to create a GridResource object.
double baud_rate = 10000.0; // communication speed
@@ -172,13 +165,10 @@
LinkedList holidays = new LinkedList();
GridResource gridRes = null;
- ResourceCalendar resCalendar = new ResourceCalendar(time_zone,
- peakLoad, offPeakLoad, holidayLoad, weekends,
- holidays, seed);
-
try {
- gridRes = new GridResource(name, baud_rate, resConfig,
- resCalendar, policy);
+ gridRes = new GridResource(name, baud_rate, seed,
+ resConfig, peakLoad, offPeakLoad, holidayLoad, weekends,
+ holidays);
}
catch (Exception e) {
e.printStackTrace();
Modified: branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues02.java
===================================================================
--- branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues02.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/examples/examples/workload/parallel/TurboExampleMultiEBQueues02.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -7,7 +7,7 @@
import gridsim.MachineList;
import gridsim.ResourceCalendar;
import gridsim.turbo.MultipleEasyBackfillingQueues;
-import gridsim.turbo.QueuePredicate;
+import gridsim.turbo.QueuePartitionPredicate;
import gridsim.turbo.SSGridlet;
import gridsim.turbo.TResourceCharacteristics;
import gridsim.util.Workload;
@@ -145,7 +145,7 @@
// this resource will use an aggressive backfilling policy (EASY)
TResourceCharacteristics resConfig = new TResourceCharacteristics(
- arch, os, mList, TResourceCharacteristics.EB_PARALLEL_SPACE_SHARED,
+ arch, os, mList, TResourceCharacteristics.MULTIPLE_EASY_BACKFILLING_QUEUES,
time_zone, cost);
MultipleEasyBackfillingQueues policy = null;
@@ -160,8 +160,8 @@
QueuePredicateExample pred1 = new QueuePredicateExample(0, 10000, peRating);
QueuePredicateExample pred2 = new QueuePredicateExample(10000, Integer.MAX_VALUE, peRating);
- policy.createQueue(0, resConfig.getNumPE() / 2, pred1);
- policy.createQueue(1, resConfig.getNumPE() / 2, pred2);
+ policy.createPartition(0, resConfig.getNumPE() / 2, pred1);
+ policy.createPartition(1, resConfig.getNumPE() / 2, pred2);
//////////////////////////////////////////
// 6. Finally, we need to create a GridResource object.
@@ -197,7 +197,7 @@
}
} // end class
-class QueuePredicateExample implements QueuePredicate {
+class QueuePredicateExample implements QueuePartitionPredicate {
int minRuntime_;
int maxRuntime_;
int resRating_;
Modified: branches/gridsim4.0-branch3/source/gridsim/gui/DefaultGridSimVisualizer.java
===================================================================
--- branches/gridsim4.0-branch3/source/gridsim/gui/DefaultGridSimVisualizer.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/source/gridsim/gui/DefaultGridSimVisualizer.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -14,9 +14,12 @@
import gridsim.ResourceCharacteristics;
import java.awt.BorderLayout;
+import java.awt.FlowLayout;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
+import java.awt.event.MouseEvent;
+import java.awt.event.MouseListener;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
@@ -76,6 +79,7 @@
private JButton btChangePause_;
private JTextField tfRunUntil_;
+ private JLabel status_;
private JList jlResource_;
private JTextArea jlResourceInfo_;
@@ -197,11 +201,38 @@
mainPanel.add(simulationPanel);
mainPanel.add(resourceInfoPanel);
+ JPanel statusPanel = new JPanel();
+ statusPanel.setLayout(new FlowLayout(FlowLayout.LEFT));
+ status_ = new JLabel("Current simulation time is " + GridSim.clock() + " seconds.");
+ statusPanel.add(status_);
+
+ /* to show simulation time when mouse cursor passing over buttons */
+ MouseListener mouseListener = new MouseListener() {
+
+ public void mouseEntered(MouseEvent e) {
+ status_.setText("Current simulation time is " + GridSim.clock() + " seconds.");
+ }
+
+ public void mouseExited(MouseEvent e) {
+ status_.setText(" ");
+ }
+
+ public void mouseClicked(MouseEvent e) { }
+ public void mousePressed(MouseEvent e) { }
+ public void mouseReleased(MouseEvent e) { }
+ };
+
+ btChangePause_.addMouseListener(mouseListener);
+ btRun_.addMouseListener(mouseListener);
+ btSlowMotion_.addMouseListener(mouseListener);
+ btStep_.addMouseListener(mouseListener);
+
createMenuBar();
firstClick_ = true;
super.setLocation(0, 0);
super.getContentPane().add(mainPanel, BorderLayout.CENTER);
+ super.getContentPane().add(statusPanel, BorderLayout.SOUTH);
super.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
// Creates a thread that will be responsible for starting the simulation
@@ -248,7 +279,7 @@
/**
* Handles the events generated by this frame
*/
- public void actionPerformed(ActionEvent e){
+ public void actionPerformed(ActionEvent e) {
String cmd = e.getActionCommand();
if(e.getSource() == btChangePause_) {
@@ -313,7 +344,7 @@
* Informs all the listeners about the change in the
* simulation time
*/
- private static void informListenersAboutTime() {
+ private void informListenersAboutTime() {
settings_.setTimeSpan(GridSim.clock());
Iterator<AllocationListener> iterListener = listeners_.values().iterator();
while(iterListener.hasNext()) {
@@ -322,6 +353,7 @@
new AllocationAction(AllocationAction.SIMULATION_TIME_CHANGED);
listener.allocationActionPerformed(action);
}
+ status_.setText("Current simulation time is " + GridSim.clock() + " seconds.");
}
/**
Modified: branches/gridsim4.0-branch3/source/gridsim/turbo/CBParallelSpaceShared.java
===================================================================
--- branches/gridsim4.0-branch3/source/gridsim/turbo/CBParallelSpaceShared.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/source/gridsim/turbo/CBParallelSpaceShared.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -279,7 +279,7 @@
* @pre userId > 0
* @post $none
*/
- public int gridletStatus(int gridletId,int userId){
+ public int gridletStatus(int gridletId,int userId) {
SSGridlet sgl = null;
// Look for the Gridlet in the running queue
Modified: branches/gridsim4.0-branch3/source/gridsim/turbo/MultipleEasyBackfillingQueues.java
===================================================================
--- branches/gridsim4.0-branch3/source/gridsim/turbo/MultipleEasyBackfillingQueues.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/source/gridsim/turbo/MultipleEasyBackfillingQueues.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -23,15 +23,50 @@
import java.util.LinkedList;
/**
- * Under development...
- *
+ * This class implements a non-FCFS policy to schedule parallel jobs. The
+ * policy is based on aggressive (EASY) backfilling. This policy can use
+ * multiple partitions or queues and the jobs can be directed to these partitions
+ * using a partition predicate ({@link QueuePartitionPredicate}. A partition
+ * can borrow resources from another when it requires and the resources are
+ * not being used by the other partition. The implementation of this policy is
+ * based on the following paper:
+ * <p>
+ * <ul>
+ * <li> Barry G. Lawson and Evgenia Smirni, Multiple-Queue Backfilling
+ * Scheduling with Priorities and Reservations for Parallel Systems,
+ * 2002 Workshop on Job Scheduling Strategies for Parallel
+ * Processing (JSSPP), pp. 72-87, 2002.
+ * </ul>
+ * <br>
+ * We use an availability profile to store the availability of processing
+ * elements. In order to represent the pivots (i.e. the first jobs in the
+ * partitions), we schedule them creating the entries in the availability
+ * profile. This way, we do not need to store the pivots' start times
+ * (or shadow times) and extra nodes in different variables. It also makes
+ * the search for available resources for a new pivot easier.
+ * <p>
+ * <b>LIMITATIONS:</b><br>
+ * <ul>
+ * <li> The list of machines comprising this resource must be
+ * homogeneous.
+ * <li> Local load is not considered. If you would like to simulate this,
+ * you have to model the local load as gridlets. It is more precise
+ * and faster. To do so, please check {@link Lublin99Workload}.
+ * <li> Gridlets cannot be paused nor migrated. This could be
+ * easily done, but due to time constraints, I could not
+ * implement these features.
+ * <li> This policy still neither supports priorities nor advance
+ * reservation.
+ * </ul>
+ *
* @author Marcos Dias de Assuncao
* @since GridSim Turbo Alpha 0.1
*
* @see gridsim.GridSim
* @see gridsim.ResourceCharacteristics
* @see gridsim.turbo.TAllocPolicy
- * @see gridsim.turbo.CBParallelSpaceShared
+ * @see gridsim.turbo.EBParallelSpaceShared
+ * @see gridsim.turbo.QueuePartitionPredicate
* @see gridsim.turbo.PERange
* @see gridsim.turbo.PERangeList
*/
@@ -39,10 +74,10 @@
public class MultipleEasyBackfillingQueues extends TAllocPolicy {
// Queue of running Gridlets
- protected LinkedList<MQGridlet> runningGridlets_;
+ protected LinkedList<SSGridlet> runningGridlets_;
// Queue of Gridlets waiting in this queue
- protected LinkedList<MQGridlet> queuedGridlets_;
+ protected LinkedList<SSGridlet> queuedGridlets_;
// The rating of one PE
protected int ratingPE_;
@@ -51,10 +86,10 @@
protected TResourceCharacteristics resource_;
// The availability profile
- protected Profile profile_;
+ protected MultiPartitionProfile profile_;
- // the number of queues in this scheduler
- private int numQueues_;
+ // the number of partitions or queues in this scheduler
+ private int numPartitions_;
// the last time when the schedule updated was called
private double lastScheduleUpdate_;
@@ -66,12 +101,14 @@
private static final int UNKNOWN = -1;
/**
- * Allocates a new <tt>EBParallelSpaceShared</tt> object
+ * Allocates a new <tt>MultiEasyBackfillingQueues</tt> object.
+ * If the policy is create with only one partition, it will then work as
+ * a normal aggressive (EASY) backfilling scheduler.
*
* @param resourceName the <tt>GridResource</tt> entity name that will
* contain this allocation policy
* @param entityName this object entity name
- * @param numQueues The number of queues in the scheduler
+ * @param numPartitions The number of partitions of the scheduling queue
* @throws Exception This happens when one of the following scenarios occur:
* <ul>
* <li> Creating this entity before initialising GridSim package
@@ -87,28 +124,55 @@
* String[], String[], String)
*/
public MultipleEasyBackfillingQueues(String resourceName,
- String entityName, int numQueues) throws Exception {
+ String entityName, int numPartitions) throws Exception {
super(resourceName, entityName);
// makes sure that the scheduler has at least one queue
- if(numQueues <= 0) {
- throw new ParameterException("Number of queues" +
+ if(numPartitions <= 0) {
+ throw new ParameterException("Number of partitions " +
"should be larger than 1");
}
// initialises local data structure
- runningGridlets_ = new LinkedList<MQGridlet>();
- queuedGridlets_ = new LinkedList<MQGridlet>();
- numQueues_ = numQueues;
- profile_ = new Profile();
+ runningGridlets_ = new LinkedList<SSGridlet>();
+ queuedGridlets_ = new LinkedList<SSGridlet>();
+ numPartitions_ = numPartitions;
+ profile_ = new MultiPartitionProfile();
lastScheduleUpdate_ = 0.0D;
ratingPE_ = 0;
}
-
- public boolean createQueue(int queueId, int numPE, QueuePredicate predicate) {
- EasyBackFillingQueue queue = new EasyBackFillingQueue(queueId, numPE, predicate);
- profile_.addQueue(queue);
+ /**
+ * Creates a new partition in this scheduler.
+ * @param queueId the id of the partition
+ * @param numPE the number of PEs in this partition
+ * @param predicate the predicate to be used to select
+ * gridlets for this partition.
+ * @return <tt>true</tt> if the partition has been set
+ * correctly or <tt>false</tt> otherwise.
+ */
+ public boolean createPartition(int queueId, int numPE,
+ QueuePartitionPredicate predicate) {
+ if(numPE < 0) {
+ System.out.println(super.get_name() + ".createPartition(): " +
+ "Error, the number of PEs should be > 0");
+ return false;
+ }
+ else if(predicate == null) {
+ System.out.println(super.get_name() + ".createPartition(): " +
+ "Error, you have provided an invalid predicate");
+ return false;
+ }
+ else if(profile_.queues_.size() == numPartitions_
+ && !profile_.queues_.containsKey(queueId) ) {
+ System.out.println(super.get_name() + ".createPartition(): " +
+ "Error, you have already specified all the " +
+ numPartitions_ + " partitions.");
+ return false;
+ }
+
+ QueuePartition partition = new QueuePartition(queueId, numPE, predicate);
+ profile_.queues_.put(queueId, partition);
return true;
}
@@ -124,47 +188,45 @@
// of one PE assuming that the machines are homogeneous
ratingPE_ = resource_.getMIPSRatingOfOnePE();
- if(numQueues_ > 1 && profile_.getNumberOfQueues() != numQueues_) {
+ int partInProfile = profile_.queues_.size();
+ if(numPartitions_ > 1 && partInProfile != numPartitions_) {
System.out.println(super.get_name() + ".body(): The scheduler" +
- " is expected to have " + numQueues_ + " queues. However," +
- " only " + profile_.getNumberOfQueues() + " have been defined");
+ " is expected to have " + numPartitions_ + " queues. However," +
+ " only " + partInProfile + " have been defined");
return;
}
+ else if (profile_.getNumberOfAssignedPEs() > resource_.getNumPE()) {
+ System.out.println(super.get_name() + ".body(): " +
+ "Error, you have assigned more PEs to the queues than available "+
+ "at the resource");
+ return;
+ }
- //TODO: To validate the processing elements assigned to the queues
-
- // if the user has not specified the queues and the scheduler is
- // expected to have only one queue, then creates the queue and
- // includes it in the list.
- if(profile_.getNumberOfQueues() == 0 && numQueues_ == 1) {
- // creates the accept all predicate
- QueuePredicate predicate = new QueuePredicate() {
+ // if the user has not specified the partitions and the scheduler is
+ // expected to have only one partition. So, it creates the partition and
+ // assigns an accept-all predicate to it.
+ if(partInProfile == 0 && numPartitions_ == 1) {
+ QueuePartitionPredicate predicate = new QueuePartitionPredicate() {
public boolean match(SSGridlet gridlet) {
return true;
}
};
- EasyBackFillingQueue queue =
- new EasyBackFillingQueue(0, resource_.getNumPE(), predicate);
- queue.idlePERanges_ = resource_.getFreePERanges().clone();
- profile_.addQueue(queue);
+ QueuePartition partition =
+ new QueuePartition(0, resource_.getNumPE(), predicate);
+
+ partition.idlePERanges_ = resource_.getFreePERanges().clone();
+ profile_.queues_.put(partition.partitionId_, partition);
}
- // assigns the PEs to the queues
+ // divides the PEs and assigns them to the partitions
else {
int allocPE = 0;
PERangeList freeRanges = resource_.getFreePERanges().clone();
- for(EasyBackFillingQueue queue : profile_.queues_.values()) {
- allocPE += queue.initialNumPEs_;
-
- if(allocPE > resource_.getNumPE()) {
- System.out.println(super.get_name() + ".body(): The scheduler" +
- " cannot allocate PEs to all queues because there are not" +
- " anough PEs");
- return;
- }
-
- PERangeList selected = super.selectPERangeList(queue.initialNumPEs_, freeRanges);
- queue.idlePERanges_ = selected;
+ for(QueuePartition partition : profile_.queues_.values()) {
+ allocPE += partition.initialNumPEs_;
+ PERangeList selected =
+ super.selectPERangeList(partition.initialNumPEs_, freeRanges);
+ partition.idlePERanges_ = selected;
freeRanges = PERangeList.difference(freeRanges, selected);
}
}
@@ -192,10 +254,17 @@
}
// reset variables to default values
- runningGridlets_.clear();
+ runningGridlets_.clear();
+ queuedGridlets_.clear();
+ profile_.clear();
lastScheduleUpdate_ = 0.0D;
ratingPE_ = 0;
resource_.resetFreePERanges();
+
+ for(QueuePartition partition : profile_.queues_.values()) {
+ partition.idlePERanges_ = null;
+ partition.pivot_ = null;
+ }
}
/**
@@ -230,7 +299,7 @@
}
// Create a resource Gridlet
- MQGridlet sgl = new MQGridlet(gridlet);
+ SSGridlet sgl = new SSGridlet(gridlet);
//-------------- FOR DEBUGGING PURPOSES ONLY --------------
@@ -258,7 +327,7 @@
return;
}
- sgl.setQueueID(queueId);
+ sgl.setPartitionID(queueId);
// If there are no jobs in the queue list, then check if
// there are enough PEs to process the job immediately
@@ -270,9 +339,6 @@
queuedGridlets_.add(sgl);
}
-// System.out.println("\nFree Ranges=" + profile_.getIdlePEsPerQueue());
-// System.out.println(profile_);
-
//------------------ FOR DEBUGGING PURPOSES ONLY ----------------
// Notifies the listeners that a Gridlet has been either scheduled
@@ -362,32 +428,33 @@
// -------------------- PRIVATE METHODS ----------------------------
/**
- *
+ * Tries to start a gridlet if there are enough processing elements
+ * available at the current simulation time.
+ * @param sgl the gridlet to be started
*/
- private boolean startGridlet(MQGridlet sgl) {
+ private boolean startGridlet(SSGridlet sgl) {
int reqPE = sgl.getNumPE();
if(reqPE > resource_.getNumFreePE())
return false;
- boolean success = false; // to test various conditions
- int queueId = sgl.getQueueID();
+ boolean success = false; // to test a few conditions
+ int queueId = sgl.getPartitionID();
- // calculate the execution time of the Gridlet
double executionTime =
super.forecastExecutionTime(ratingPE_, sgl.getRemainingLength());
+
+ double currentTime = GridSim.clock() ;
// calculates how much ahead to look into the availability profile
- double currentTime = GridSim.clock() ;
-
// the Gridlet's expected finish time if it starts now
double finishTime = currentTime + executionTime;
+ // checks the availability of PEs in the selected partition
PERangeList ranges =
profile_.getImmediateAvailability(queueId, executionTime);
-
- // if the above method returns null, it means that there are not enough
- // PEs to serve the reservation or Gridlet
+
+ // if there are enough PEs in the queue, then allocate them
if(ranges.getNumPE() >= reqPE) {
ranges = super.selectPERangeList(reqPE, ranges);
profile_.allocateImmediateRanges(queueId, finishTime, ranges);
@@ -395,34 +462,27 @@
}
// If the queue to which the gridlet is assigned does not have the
- // required PEs, then try to borrow the additional PEs from other queues.
+ // required PEs, then tries to borrow the additional PEs from other queues
if(!success) {
+ // gets all available PEs during given time interval
PERangeList overallAvailPEs =
profile_.getImmediateAvailability(executionTime);
// additional PEs required
int addRequired = reqPE - ranges.getNumPE();
+ // removes PEs already obtained from selected partition
PERangeList addRanges =
PERangeList.difference(overallAvailPEs, ranges);
if(addRanges != null && addRanges.getNumPE() >= addRequired) {
- // subtracts the ranges already obtained from the gridlet's queue
-
-// System.out.println("\nRanges to Add to queue " + queueId +" = " +
-// addRanges + "\noverall = " + overallAvailPEs +
-// "\n overall num available = " + overallAvailPEs.getNumPE() +
-// "\n free PEs = " + resource_.getNumFreePE() +
-// "\n free PEs profile = " + profile_.getNumFreePEs() +
-// "\n PEs from the queue = " + ranges.getNumPE() +
-// "\n req PEs = " + reqPE);
-
- // borrows the ranges from the queues and adds it into the
- // specified queue
+
+ // borrows the additional PEs required from the partitions
+ // and adds them into the specified queue
addRanges = super.selectPERangeList(addRequired, addRanges);
profile_.transferPEs(queueId, addRanges, currentTime, finishTime);
- // allocate the ranges to the job
+ // allocates the ranges to the gridlet
ranges.addAll(addRanges);
profile_.allocateImmediateRanges(queueId, finishTime, ranges);
success = true;
@@ -430,7 +490,7 @@
}
if(!success)
- return false;
+ return false; // it was not possible to schedule the gridlet
// sets the PEs to busy at resource class. This is just to provide
// information to other classes that may query it
@@ -462,13 +522,17 @@
}
/**
+ * Tries to schedule a gridlet. Only the first job in the waiting queue
+ * for a given partition is scheduled. If a pivot for that partition already
+ * exists, them the method returns <tt>null</tt>
* @param sgl the resource gridlet
+ * return <tt>true</tt> if gridlet was scheduled; <tt>false</tt> otherwise.
*/
- private boolean scheduleGridlet(MQGridlet sgl) {
+ private boolean scheduleGridlet(SSGridlet sgl) {
int reqPE = sgl.getNumPE();
- int queueId = sgl.getQueueID();
+ int queueId = sgl.getPartitionID();
- EasyBackFillingQueue queue = profile_.getQueue(queueId);
+ QueuePartition queue = profile_.getQueue(queueId);
// if queue has a pivot already, then just add
// the job to the waiting queue
@@ -485,10 +549,13 @@
double startTime = -1; // keep the potential start time of the gridlet
double finishTime = -1; // store the gridlet's expected finish time
- // check whether there are PEs available over the time interval requested
+ // check when enough PEs to handle the gridlet will be available at
+ // the partition without borrowing PEs
Object[] availObjQueue =
profile_.checkPERangesAvailability(queueId, reqPE, executionTime);
+ // check when enough PEs to handle the gridlet will be available
+ // considering all the partitions
Object[] availObj =
profile_.checkPERangesAvailability(reqPE, executionTime);
@@ -501,11 +568,12 @@
startTimeQueue=profile_.get(anchor).getTime();
}
-// System.out.println(profile_);
-
anchor = (Integer)availObj[0];
double startTimeAll = profile_.get(anchor).getTime();
+ // if the time if the selected partition is smaller or the same as
+ // considering all the partitions, so that means that we can select
+ // resources from the selected partition
if(startTimeQueue <= startTimeAll) {
ranges = (PERangeList)availObjQueue[2];
ranges = super.selectPERangeList(reqPE, ranges);
@@ -524,7 +592,8 @@
else {
PERangeList addRanges = (PERangeList)availObj[2];
- // the anchor index, the entry in the profile where the gridlet will be placed
+ // the anchor index, the entry in the profile where
+ // the gridlet will be placed
int anchorIndex = (Integer)availObj[0];
// insert index represents the position after which the entry
// corresponding to the gridlet's finish time will be placed
@@ -534,16 +603,19 @@
startTime = startTimeAll;
finishTime = startTime + executionTime;
+ // checks what PEs from those selected already belong
+ // to the gridlet's partition
availObjQueue = profile_.checkPERangesAvailability(queueId,
startTime, executionTime);
- ranges = availObjQueue == null ? new PERangeList() : (PERangeList)availObjQueue[2];
- addRanges = availObjQueue == null ? addRanges : PERangeList.difference(addRanges, ranges);
+ ranges = availObjQueue == null ? new PERangeList() :
+ (PERangeList)availObjQueue[2];
+
+ addRanges = availObjQueue == null ? addRanges :
+ PERangeList.difference(addRanges, ranges);
+
addRanges = super.selectPERangeList(reqPE - ranges.getNumPE(), addRanges);
-// System.out.println("\nRanges to transfer to queue " + queueId +" = " +
-// addRanges + " from " + startTime + " to " + finishTime);
-
// borrows the ranges from the queues and adds it into the
// specified queue
profile_.transferPEs(queueId, addRanges, startTime, finishTime);
@@ -647,9 +719,9 @@
int itemsFinished = 0;
// iterates the list to check what has finished
- Iterator<MQGridlet> iter = runningGridlets_.iterator();
+ Iterator<SSGridlet> iter = runningGridlets_.iterator();
while (iter.hasNext()) {
- MQGridlet gridlet = iter.next();
+ SSGridlet gridlet = iter.next();
// as gridlets are removed from running queue once they finish
// time is smaller than current time, then testing the time
// is enough. There's no need to check status
@@ -675,7 +747,7 @@
// first checks whether the pivots can be started
// checks the pivots first
- for(EasyBackFillingQueue queue : profile_.queues_.values()) {
+ for(QueuePartition queue : profile_.queues_.values()) {
if(queue.pivot_ != null && queue.pivot_.getStartTime() <= currentTime) {
runningGridlets_.add(queue.pivot_);
queuedGridlets_.remove(queue.pivot_);
@@ -691,9 +763,9 @@
// Start the execution of Gridlets that are queued and whose
// potential start execution time is smaller than reference time
- Iterator<MQGridlet> iter = queuedGridlets_.iterator();
+ Iterator<SSGridlet> iter = queuedGridlets_.iterator();
while (iter.hasNext()) {
- MQGridlet gridlet = iter.next();
+ SSGridlet gridlet = iter.next();
if(gridlet.getStartTime() < 0) {
boolean success = startGridlet(gridlet);
@@ -725,73 +797,53 @@
super.sendFinishGridlet( sgl.getGridlet() );
}
-
- private class EasyBackFillingQueue {
- int queueId_; // this queue's identifier
+ // ---------------------- PRIVATE CLASSES ------------------------
+
+ /**
+ * This class represents a partition in this scheduler. It only
+ * stores a few variables used to control the partition.
+ * @author Marcos Dias de Assuncao
+ * @since GridSim Turbo Alpha 0.1
+ */
+ private class QueuePartition {
+ int partitionId_; // this partition's identifier
int initialNumPEs_; // the initial number of PEs allocated
- PERangeList idlePERanges_; // idle resources in this queue
- MQGridlet pivot_; // the first job of this queue in the general waiting queue
+ PERangeList idlePERanges_; // idle resources in this partition
+ SSGridlet pivot_; // the first job of this queue in the general waiting queue
// to check whether a gridlet can be scheduled in this queue
- QueuePredicate predicate_;
+ QueuePartitionPredicate predicate_;
- protected EasyBackFillingQueue(int queueId,
- int numPE, QueuePredicate predicate) {
- this.queueId_ = queueId;
+ protected QueuePartition(int queueId,
+ int numPE, QueuePartitionPredicate predicate) {
+ this.partitionId_ = queueId;
initialNumPEs_ = numPE;
predicate_ = predicate;
pivot_ = null;
}
-
- protected int getNumIdlePEs() {
- return (idlePERanges_ == null) ? 0 : idlePERanges_.getNumPE();
- }
}
- private class MQGridlet extends SSGridlet {
- private int queueId_;
- private int priority_;
-
- public MQGridlet(Gridlet gridlet) {
- super(gridlet);
- queueId_ = UNKNOWN;
- }
-
- public void setQueueID(int queueId) {
- queueId_ = queueId;
- }
-
- public int getQueueID() {
- return queueId_;
- }
-
- public int getPriority() {
- return priority_;
- }
-
- public void setPriority(int priority) {
- this.priority_ = priority;
- }
- }
-
/**
- * This class represents an entry in the usage profile. There is an entry
+ * This class represents an entry in the profile. There is an entry
* at most in the usage profile for each job scheduled by this policy.
*
* @author Marcos Dias de Assuncao
* @since GridSim Turbo Alpha 0.1
*/
private class ProfileEntry {
+ // the ranges available
+ private HashMap <Integer, PERangeList> ranges_;
+ // the time when the ranges will be available
+ private double time_;
+ // number of gridlets that rely on this entry
+ // to mark their completion time or anchor point
+ private int numGridlets_ = 1;
- private HashMap <Integer, PERangeList> ranges_; // the ranges available
- private double time_; // the time when the ranges will be available
- private int numGridlets_ = 1; // number of gridlets that rely on this entry
- // to mark their completion time or anchor point
/**
* Creates an instance of @link{ProfileEntry}.
* @param time the time associated with this event
*/
- public ProfileEntry(double time) {
+ protected ProfileEntry(double time) {
time_ = time;
ranges_ = new HashMap<Integer, PERangeList>();
}
@@ -801,11 +853,15 @@
* @param queue the queue whose ranges should be obtained
* @return the ranges of free PEs associated with this entry
*/
- public PERangeList getPERanges(int queue) {
+ protected PERangeList getPERanges(int queue) {
return ranges_.get(queue);
}
-
- public PERangeList getPERanges() {
+
+ /**
+ * Returns the general ranges of free PEs associated with this entry
+ * @return the ranges of free PEs associated with this entry
+ */
+ protected PERangeList getPERanges() {
PERangeList result = new PERangeList();
for(PERangeList list : ranges_.values()) {
if(list.getNumPE() > 0)
@@ -819,12 +875,13 @@
* @param queue the queue whose ranges should be set
* @param list the range of PEs
*/
- public void setPERangeList(int queue, PERangeList list) {
+ protected void setPERangeList(int queue, PERangeList list) {
ranges_.put(queue, list);
// testNumPEs();
}
- private void testNumPEs() {
+ // FOR DEBUGGING PURPOSES ONLY
+ protected void testNumPEs() {
try {
if(getNumPE() > resource_.getNumPE())
throw new Exception("Entry contains more PEs than the maximum allowed");
@@ -834,22 +891,21 @@
System.exit(1);
}
}
-
/**
* Returns the time associated with this entry
* @return the time associated
*/
- public double getTime() {
+ protected double getTime() {
return time_;
}
/**
* Gets the number of PEs associated with this entry
* @param queue the queue whose number of PEs be obtained
- * @return the number of PEs
+ * @return the number of PEs available for the queue
*/
- public int getNumPE(int queue) {
+ protected int getNumPE(int queue) {
PERangeList ranges = getPERanges(queue);
if(ranges == null)
return 0;
@@ -857,38 +913,43 @@
return ranges.getNumPE();
}
- public int getNumPE() {
+ /**
+ * Gets the number of PEs associated with this entry
+ * @return the number of PEs
+ */
+ protected int getNumPE() {
int numPE = 0;
for(PERangeList list : ranges_.values()) {
numPE += list.getNumPE();
}
return numPE;
}
-
- public void transferPEs(int recQueueId, PERangeList list) {
-
+
+ /**
+ * Transfers PEs from partitions to one selected partition
+ * @param recQueueId the partition receiving the ranges
+ * @param list the list of ranges
+ */
+ protected void transferPEs(int recQueueId, PERangeList list) {
for(Integer queueId : ranges_.keySet()) {
-// if(queueId != recQueueId) {
- PERangeList uptList = PERangeList.difference(ranges_.get(queueId), list);
- if(uptList == null)
- uptList = new PERangeList();
- ranges_.put(queueId, uptList);
-// }
+ PERangeList uptList = PERangeList.difference(ranges_.get(queueId), list);
+ if(uptList == null)
+ uptList = new PERangeList();
+ ranges_.put(queueId, uptList);
}
PERangeList queueList = ranges_.get(recQueueId);
queueList.addAll(list.clone());
queueList.mergePERanges();
ranges_.put(recQueueId, queueList);
-
-// testNumPEs();
+// testNumPEs(); // for debugging purposes
}
/**
* Sets the time associated with this event
* @param time the time to be set
*/
- public void setTime(double time) {
+ protected void setTime(double time) {
time_ = time;
}
@@ -896,7 +957,7 @@
* Increases the number of Gridlets that rely on this entry to mark
* their expected completion time or their anchor point
*/
- public void increaseGridlet() {
+ protected void increaseGridlet() {
numGridlets_++;
}
@@ -904,7 +965,7 @@
* Decreases the number of Gridlets that rely on this entry to mark
* their expected completion time or their anchor point
*/
- public void decreaseGridlet() {
+ protected void decreaseGridlet() {
numGridlets_--;
}
@@ -913,7 +974,7 @@
* their expected completion time or their anchor point
* @return the number of Gridlets that use this entry
*/
- public int getNumGridlets() {
+ protected int getNumGridlets() {
return numGridlets_;
}
@@ -923,7 +984,7 @@
* @param time the time for the cloned entry
* @return the cloned entry
*/
- public ProfileEntry clone(double time) {
+ protected ProfileEntry clone(double time) {
ProfileEntry clone = new ProfileEntry(time);
for(Integer queueId : ranges_.keySet()) {
PERangeList clonedRanges = ranges_.get(queueId).clone();
@@ -953,59 +1014,60 @@
/**
* This class represents the profile containing the ranges of PEs
* available at given simulation times
+ *
* @author Marcos Dias de Assuncao
* @since GridSim Turbo Alpha 0.1
*/
- private class Profile extends ArrayList<ProfileEntry> {
+ private class MultiPartitionProfile extends ArrayList<ProfileEntry> {
private static final long serialVersionUID = -1853610061073508770L;
// The queues used by this scheduler
- HashMap<Integer, EasyBackFillingQueue> queues_;
+ HashMap<Integer, QueuePartition> queues_;
/**
* Creates a new @link{AvailabilityProfile} object.
*/
- public Profile() {
+ protected MultiPartitionProfile() {
super();
- queues_ = new HashMap<Integer, EasyBackFillingQueue>();
+ queues_ = new HashMap<Integer, QueuePartition>();
}
- public void addQueue(EasyBackFillingQueue queue) {
- queues_.put(queue.queueId_, queue);
+ /**
+ * Returns the number of PEs assigned to the partitions
+ * @return the number of PEs assigned to the partitions
+ */
+ protected int getNumberOfAssignedPEs() {
+ int numPEs = 0;
+ for(QueuePartition queue : queues_.values()) {
+ numPEs += queue.initialNumPEs_;
+ }
+ return numPEs;
}
- public int getNumberOfQueues() {
- return queues_.size();
- }
-
-
- public EasyBackFillingQueue getQueue(int queueId) {
+ /**
+ * Gets a partition with the given ID
+ * @param queueId the id of the partition
+ * @return the partition with the given ID
+ */
+ protected QueuePartition getQueue(int queueId) {
return queues_.get(queueId);
}
- public int getCorrespondingQueue(SSGridlet sgl) {
- for(EasyBackFillingQueue queue : queues_.values()) {
+ /**
+ * Gets the able to handle the given gridlet
+ * @param sgl the gridlet for which a partition is to be found
+ * @return the partition ID
+ */
+ protected int getCorrespondingQueue(SSGridlet sgl) {
+ for(QueuePartition queue : queues_.values()) {
if(queue.predicate_.match(sgl))
- return queue.queueId_;
+ return queue.partitionId_;
}
return UNKNOWN;
}
/**
- * Returns a clone of this object.<br>
- * <b>NOTE:</b> this method does not clone the entries
- * @return the cloned object
- */
- public Profile clone() {
- Profile clone = new Profile();
- for(ProfileEntry entry : this){
- clone.add(entry);
- }
- return clone;
- }
-
- /**
* Returns the entry whose time is closest to the <tt>time</tt> given but
* smaller, or whose time is equals to <tt>time</tt>
* @param time the time to be used to search for the entry
@@ -1032,8 +1094,10 @@
* entries whose date is smaller or equals to refTime will
* be removed.
* @param refTime the reference time to be used for entry removal.
+ * @return the last entry removed or <tt>null</tt> if no
+ * entry has been removed
*/
- public ProfileEntry removePastEntries(double refTime) {
+ protected ProfileEntry removePastEntries(double refTime) {
// Update the availability profile
ProfileEntry lastRemoved = null;
Iterator<ProfileEntry> iterProfile = super.iterator();
@@ -1051,23 +1115,27 @@
return lastRemoved;
}
+ /**
+ * Updates the idle PEs at the queues based on a given profile entry
+ * @param status the profile entry to bed used
+ */
protected void setCurrentStatus(ProfileEntry status) {
- for(EasyBackFillingQueue queue : queues_.values()) {
- queue.idlePERanges_ = status.getPERanges(queue.queueId_).clone();
+ for(QueuePartition queue : queues_.values()) {
+ queue.idlePERanges_ = status.getPERanges(queue.partitionId_).clone();
}
}
/**
- * Selects a list of PE ranges able to provide enough
- * PEs to handle a Gridlet.
+ * Checks what are the PEs available for the specified queue during
+ * the given time duration.
* @param duration the duration of the Gridlet
- * @return the list of ranges of PEs that can be used by the gridlet.
- * Note that this method may return more PEs than the gridlet requires.
+ * @return the list of ranges of PEs that can be used
+ * during the given period.
*/
- private PERangeList getImmediateAvailability(int queueId, double duration) {
+ protected PERangeList getImmediateAvailability(int queueId, double duration) {
double startTime = GridSim.clock(); // start time is now
- EasyBackFillingQueue queue = queues_.get(queueId);
+ QueuePartition queue = queues_.get(queueId);
// the gridlet's expected finish time
double finishTime = startTime + duration;
@@ -1076,8 +1144,8 @@
PERangeList intersectList = queue.idlePERanges_.clone();
// scan the availability profile until the expected termination
- // of the Gridlet to check whether enough PEs will be available
- // for the Gridlet. Stop the search if not enough PEs are available
+ // of the Gridlet to check what PEs will be available. Stops the
+ // search if no PEs are found at a particular time
for(ProfileEntry entry : this) {
double entryTime = entry.getTime();
if(entryTime < startTime) {
@@ -1092,27 +1160,31 @@
if(entryTime < finishTime) {
PERangeList listEntry = entry.getPERanges(queueId);
intersectList = PERangeList.intersection(intersectList, listEntry);
- if(intersectList == null)
+ if(intersectList == null || intersectList.getNumPE() == 0)
break;
}
}
}
- // return null if the number of PEs available over the required
- // time interval is smaller than what the Gridlet/Reservation requires
+ // To avoid returning null
if(intersectList == null) {
- return new PERangeList();
+ intersectList = new PERangeList();
}
// the PEs that can be used by the gridlet
return intersectList;
}
-
+ /**
+ * Creates an entry to be used as anchor when the profile is empty.
+ * The entry is based on the currently idle PEs at the partitions
+ * @param time the time for the entry
+ * @return the entry created.
+ */
private ProfileEntry createHeadEntry(double time) {
ProfileEntry entry = new ProfileEntry(time);
- for(EasyBackFillingQueue queue : queues_.values()) {
- entry.setPERangeList(queue.queueId_, queue.idlePERanges_.clone());
+ for(QueuePartition queue : queues_.values()) {
+ entry.setPERangeList(queue.partitionId_, queue.idlePERanges_.clone());
}
return entry;
}
@@ -1120,14 +1192,15 @@
/**
* Allocates a list of PE ranges to a gridlet or and updates the
* availability profile accordingly
+ * @param queueId the partition from which PEs have been selected
* @param finishTime the finish time of the Gridlet
* @param selected the list of PE ranges selected
*/
- public void allocateImmediateRanges(int queueId, double finishTime,
+ protected void allocateImmediateRanges(int queueId, double finishTime,
PERangeList selected) {
double startTime = GridSim.clock(); // start time is now
- EasyBackFillingQueue queue = queues_.get(queueId);
+ QueuePartition queue = queues_.get(queueId);
// check whether a new tail is needed to mark the end of the request
ProfileEntry tailEntry = getPrecedingEntry(finishTime);
@@ -1154,53 +1227,37 @@
continue;
}
else {
- PERangeList difference = PERangeList.difference(entry.getPERanges(queueId), selected);
+ PERangeList difference =
+ PERangeList.difference(entry.getPERanges(queueId), selected);
difference = difference == null ? new PERangeList() : difference;
entry.setPERangeList(queueId, difference);
}
}
- PERangeList difference = PERangeList.difference(queue.idlePERanges_, selected);
+ PERangeList difference = PERangeList.difference(queue.idlePERanges_, selected);
+ // avoid idle PEs from being null
difference = difference == null ? new PERangeList() : difference;
- queue.idlePERanges_ = difference;
+ queue.idlePERanges_ = difference;
}
- /*
+ /**
* Gets the idle PEs in all queues
*/
- private PERangeList getOverallIdlePEs() {
+ protected PERangeList getOverallIdlePEs() {
PERangeList idlePEs = new PERangeList();
- for(EasyBackFillingQueue queue: queues_.values()) {
+ for(QueuePartition queue: queues_.values()) {
if(queue.idlePERanges_.getNumPE() > 0)
idlePEs.addAll(queue.idlePERanges_.clone());
}
return idlePEs;
}
- private ProfileEntry getIdlePEsPerQueue() {
- ProfileEntry entry = new ProfileEntry(GridSim.clock());
- for(EasyBackFillingQueue queue: queues_.values()) {
- entry.setPERangeList(queue.queueId_, queue.idlePERanges_.clone());
- }
- return entry;
- }
-
- private int getNumFreePEs() {
- int freePE = 0;
- for(EasyBackFillingQueue queue: queues_.values()) {
- freePE += queue.idlePERanges_.getNumPE();
- }
- return freePE;
- }
-
/**
- * Selects a list of PE ranges able to provide enough
- * PEs to handle a Gridlet.
+ * Checks what PE ranges are available during the given interval.
* @param duration the duration of the Gridlet
- * @return the list of ranges of PEs that can be used by the gridlet.
- * Note that this method may return more PEs than the gridlet requires.
+ * @return the list of ranges of PEs available
*/
- private PERangeList getImmediateAvailability(double duration) {
+ protected PERangeList getImmediateAvailability(double duration) {
double startTime = GridSim.clock(); // start time is now
@@ -1211,8 +1268,8 @@
PERangeList intersectList = getOverallIdlePEs();
// scan the availability profile until the expected termination
- // of the Gridlet to check whether enough PEs will be available
- // for the Gridlet. Stop the search if not enough PEs are available
+ // of the Gridlet to check what PEs will be available until the
+ // finishTime. Stops the search if it finds null resources
for(ProfileEntry entry : this) {
double entryTime = entry.getTime();
if(entryTime < startTime) {
@@ -1227,24 +1284,33 @@
if(entryTime < finishTime) {
PERangeList listEntry = entry.getPERanges();
intersectList = PERangeList.intersection(intersectList, listEntry);
- if(intersectList == null)
+ if(intersectList == null || intersectList.getNumPE() == 0)
break;
}
}
}
- // return null if the number of PEs available over the required
- // time interval is smaller than what the Gridlet/Reservation requires
+ // to avoid returning null
if(intersectList == null) {
- return new PERangeList();
+ intersectList = new PERangeList();
}
// the PEs that can be used by the gridlet
return intersectList;
}
- /*
- *
+ /**
+ * Checks when anough PEs ranges will be available at a given queue to
+ * handle a given gridlet
+ * @param queueId the selected queue
+ * @param reqPE the number of PEs required
+ * @param duration the duration of the gridlet
+ * @return an array where:
+ * array[0] = index of entry used as anchor
+ * array[1] = index of entry closest to the completion
+ * array[2] = the list of PEs available at that time
+ * or <tt>null</tt> if not enough pes will be available at the queue at
+ * any time
*/
protected Object[] checkPERangesAvailability(int queueId,
int reqPE, double duration) {
@@ -1341,8 +1407,15 @@
return result;
}
- /*
- *
+ /**
+ * Checks when anough PEs ranges will be available at all queues to
+ * handle a given gridlet
+ * @param reqPE the number of PEs required
+ * @param duration the duration of the gridlet
+ * @return an array where:
+ * array[0] = index of entry used as anchor
+ * array[1] = index of entry closest to the completion
+ * array[2] = the list of PEs available at that time
*/
protected Object[] checkPERangesAvailability(int reqPE, double duration) {
@@ -1438,9 +1511,17 @@
return result;
}
-
-
- private void allocatePERanges(int queueId,
+ /**
+ * Allocate processing elements to a gridlet
+ * @param queueId the id of the gridlet's selected partition
+ * @param anchorIndex the index of the entry used as anchor
+ * @param tailIndex the index of the last entry close to the gridlet's
+ * finish time
+ * @param selected the selected ranges of PEs
+ * @param startTime the gridlet's start time
+ * @param finishTime the gridlet's finish time
+ */
+ protected void allocatePERanges(int queueId,
int anchorIndex, int tailIndex,
PERangeList selected, double startTime, double finishTime) {
@@ -1489,10 +1570,18 @@
}
}
- private Object[] checkPERangesAvailability(int queueId,
+ /**
+ * Checks what ranges of PEs will be available for a gridlet in its
+ * partition a given time over a period of time
+ * @param queueId the selected partition id
+ * @param startTime the start time of the gridlet
+ * @param duration the duration of the gridlet
+ * @return the ranges of PEs available
+ */
+ protected Object[] checkPERangesAvailability(int queueId,
double startTime, double duration) {
- EasyBackFillingQueue queue = queues_.get(queueId);
+ QueuePartition queue = queues_.get(queueId);
// the anchor index, the entry in the profile where
// the gridlet will be placed OR the closest entry to the
@@ -1555,8 +1644,6 @@
}
if(intersectList == null || intersectList.getNumPE() == 0) {
- // there are not enough PEs available to serve the
- // advance reservation request, then returns null
return null;
}
}
@@ -1572,25 +1659,31 @@
return result;
}
+ /**
+ * Transfers ranges of PEs from other partitons to a selected partition
+ * @param recQueueId the partition that will receive the PEs
+ * @param list the list of ranges of PEs to transfer
+ * @param startTime the start time of the transfer
+ * @param finishTime the finish time of the transfer
+ */
protected void transferPEs(int recQueueId, PERangeList list,
double startTime, double finishTime) {
-
+
+ // if start time is equals to current time, then we have
+ // to transfer ranges across the idle pes as well
if(startTime <= GridSim.clock()) {
- for(EasyBackFillingQueue queue : queues_.values()) {
-// if(queue.queueId_ != recQueueId) {
- queue.idlePERanges_ = PERangeList.difference(queue.idlePERanges_, list);
- if(queue.idlePERanges_ == null)
- queue.idlePERanges_ = new PERangeList();
-// }
+ for(QueuePartition queue : queues_.values()) {
+ queue.idlePERanges_ = PERangeList.difference(queue.idlePERanges_, list);
+ if(queue.idlePERanges_ == null)
+ queue.idlePERanges_ = new PERangeList();
}
- EasyBackFillingQueue queue = queues_.get(recQueueId);
-// queue.idlePERanges_ = PERangeList.difference(queue.idlePERanges_, list);
-// queue.idlePERanges_ = queue.idlePERanges_ == null ? new PERangeList() : queue.idlePERanges_;
+ QueuePartition queue = queues_.get(recQueueId);
queue.idlePERanges_.addAll(list.clone());
queue.idlePERanges_.mergePERanges();
}
+ // transfer the ranges
for(int i=0; i<super.size(); i++) {
ProfileEntry nextEntry = super.get(i);
if(nextEntry.getTime() < startTime)
@@ -1603,11 +1696,6 @@
}
}
}
-
- protected void releaseRanges(int queueId, PERangeList ranges) {
- EasyBackFillingQueue queue = queues_.get(queueId);
- queue.idlePERanges_.addAll(ranges.clone());
- }
/**
* Creates an string representation of the profile
Copied: branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePartitionPredicate.java (from rev 102, branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePredicate.java)
===================================================================
--- branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePartitionPredicate.java (rev 0)
+++ branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePartitionPredicate.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -0,0 +1,29 @@
+/*
+ * Title: GridSim Toolkit
+ * Description: GridSim (Grid Simulation) Toolkit for Modelling and Simulation
+ * of Parallel and Distributed Systems such as Clusters and Grids
+ * Licence: GPL - http://www.gnu.org/copyleft/gpl.html
+ */
+
+package gridsim.turbo;
+
+/**
+ * This interface is used to filter what gridlets should be put in a given
+ * partition by policies that use multiple partitions or queues. See for
+ * example {@link MultipleEasyBackfillingQueues}.
+ *
+ * @author Marcos Dias de Assuncao
+ * @since GridSim Turbo Alpha 0.1
+ */
+
+public interface QueuePartitionPredicate {
+
+ /**
+ * Checks whether a given gridlet meets the criteria of the partition.
+ * @param gridlet the gridlet to be considered for scheduling.
+ * @return <tt>true</tt> if the gridlet can be included in this
+ * partition; <tt>false</tt> otherwise.
+ */
+ boolean match(SSGridlet gridlet);
+
+}
Deleted: branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePredicate.java
===================================================================
--- branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePredicate.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/source/gridsim/turbo/QueuePredicate.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -1,28 +0,0 @@
-/*
- * Title: GridSim Toolkit
- * Description: GridSim (Grid Simulation) Toolkit for Modelling and Simulation
- * of Parallel and Distributed Systems such as Clusters and Grids
- * Licence: GPL - http://www.gnu.org/copyleft/gpl.html
- */
-
-package gridsim.turbo;
-
-/**
- * This interface is used to filter what gridlets should be put in a given
- * scheduling queue by the {@link MultipleEasyBackfillingQueues}.
- *
- * @author Marcos Dias de Assuncao
- * @since GridSim Turbo Alpha 0.1
- */
-
-public interface QueuePredicate {
-
- /**
- * Checks whether a given gridlet meet the criteria of the scheduling queue.
- * @param gridlet the gridlet to be considered for scheduling.
- * @return <tt>true</tt> whether the gridlet can be included in this
- * queue, or <tt>false</tt> otherwise.
- */
- boolean match(SSGridlet gridlet);
-
-}
Modified: branches/gridsim4.0-branch3/source/gridsim/turbo/SSGridlet.java
===================================================================
--- branches/gridsim4.0-branch3/source/gridsim/turbo/SSGridlet.java 2008-02-14 12:00:22 UTC (rev 102)
+++ branches/gridsim4.0-branch3/source/gridsim/turbo/SSGridlet.java 2008-02-15 04:13:00 UTC (rev 103)
@@ -9,6 +9,7 @@
import java.text.DecimalFormat;
+import gridsim.GridResource;
import gridsim.GridSim;
import gridsim.Gridlet;
import gridsim.gui.GridSimVisualizer;
@@ -49,7 +50,14 @@
private int numPE_;
// A list of ranges of PEs used by this Gridlet
- private PERangeList peRangeList_ = null;
+ private PERangeList peRangeList_ = null;
+
+ // the partiton or queue in the resource to which this
+ // gridlet was scheduled
+ private int partition_;
+
+ // the priority of this gridlet assigned by the scheduler
+ private int priority_;
// NOTE: Below attributes are related to AR stuff
private final int NOT_FOUND = -1;
@@ -287,6 +295,50 @@
}
/**
+ * Gets the id of the partition or queue to which this
+ * gridlet was scheduled
+ * @return the partition id or <tt>-1</tt> if not found
+ */
+ public int getPartitionID() {
+ return partition_;
+ }
+
+ /**
+ * Sets the id of the partition or queue to which this
+ * gridlet was scheduled
+ * @param partition the partition id
+ * @return <tt>true</tt> if set correctly or <tt>false</tt> otherwise.
+ */
+ public boolean setPartitionID(int partition) {
+ if(partition < 0)
+ return false;
+
+ partition_ = partition;
+ return true;
+ }
+
+ /**
+ * Gets the priority of this gridlet assigned by the scheduler
+ * @return the priority or <tt>-1</tt> if not found
+ */
+ public int getPriority() {
+ return priority_;
+ }
+
+ /**
+ * Sets the priority of this gridlet assigned by the scheduler
+ * @param priority the priority
+ * @return <tt>true</tt> if set correctly or <tt>false</tt> otherwise.
+ */
+ public boolean setPriority(int priority) {
+ if(priority < 0)
+ return false;
+
+ priority_ = priority;
+ return true;
+ }
+
+ /**
* Gets the remaining gridlet length
* @return gridlet length
* @pre $none
@@ -476,6 +528,8 @@
this.startTime_ = NOT_FOUND;
this.totalCompletionTime_ = 0.0;
this.startExecTime_ = 0.0;
+ this.partition_ = NOT_FOUND;
+ this.priority_ = NOT_FOUND;
// In case a Gridlet has been executed partially by some other grid
// ...
[truncated message content] |