[haizea-commit] r585 - in branches/TP2.0/src/haizea/resourcemanager: . scheduler

haizea-commit at mailman.cs.uchicago.edu haizea-commit at mailman.cs.uchicago.edu
Wed Jun 17 11:09:35 CDT 2009


Author: borja
Date: 2009-06-17 11:09:33 -0500 (Wed, 17 Jun 2009)
New Revision: 585

Modified:
   branches/TP2.0/src/haizea/resourcemanager/rm.py
   branches/TP2.0/src/haizea/resourcemanager/scheduler/lease_scheduler.py
   branches/TP2.0/src/haizea/resourcemanager/scheduler/vm_scheduler.py
Log:
Pushing minor changes before renaming "resourcemanager" package


Modified: branches/TP2.0/src/haizea/resourcemanager/rm.py
===================================================================
--- branches/TP2.0/src/haizea/resourcemanager/rm.py	2009-06-17 15:29:09 UTC (rev 584)
+++ branches/TP2.0/src/haizea/resourcemanager/rm.py	2009-06-17 16:09:33 UTC (rev 585)
@@ -45,6 +45,7 @@
 from haizea.resourcemanager.scheduler.lease_scheduler import LeaseScheduler
 from haizea.resourcemanager.scheduler.vm_scheduler import VMScheduler
 from haizea.resourcemanager.scheduler.slottable import SlotTable
+from haizea.resourcemanager.scheduler.policy import Policy
 from haizea.resourcemanager.scheduler.resourcepool import ResourcePool, ResourcePoolWithReusableImages
 from haizea.resourcemanager.rpcserver import RPCServer
 from haizea.common.utils import abstract, round_datetime, Singleton
@@ -153,6 +154,9 @@
         # Lease Scheduler
         self.scheduler = LeaseScheduler(vm_scheduler, preparation_scheduler, slottable)
         
+        # Policy engine
+        self.policy = Policy()
+        
         # Lease request frontends
         if clock == constants.CLOCK_SIMULATED:
             # In pure simulation, we can only use the tracefile frontend

Modified: branches/TP2.0/src/haizea/resourcemanager/scheduler/lease_scheduler.py
===================================================================
--- branches/TP2.0/src/haizea/resourcemanager/scheduler/lease_scheduler.py	2009-06-17 15:29:09 UTC (rev 584)
+++ branches/TP2.0/src/haizea/resourcemanager/scheduler/lease_scheduler.py	2009-06-17 16:09:33 UTC (rev 585)
@@ -42,30 +42,12 @@
     """The Haizea Lease Scheduler
     
     This is the main scheduling class in Haizea. It handles lease scheduling which,
-    in turn involved VM scheduling, preparation scheduling (such as transferring
+    in turn, involves VM scheduling, preparation scheduling (such as transferring
     a VM image), and numerous bookkeeping operations. All these operations are
     handled by other classes, so this class acts mostly as an orchestrator that
-    coordinates all the different operations involved in scheduling a lease.
-    
-    Public methods:
-    request_lease -- Entry point of leases into the scheduler
-    schedule -- The scheduling function
-    process_reservations -- Processes starting/ending reservations at a given time
-    cancel_lease -- Cancels a lease
-    fail_lease -- Marks a lease as failed, and does any necessary cleaning up
-    is_queue_empty -- Is the queue empty?
-    exists_scheduled_leases -- Are there any leases scheduled?
-    
-    Private methods:
-    __process_queue -- Processes queue and, if possible, schedules leases
-    __schedule_lease -- Schedules a lease
-    __preempt_lease -- Preempts a lease
-    __enqueue -- Puts a lease at the end of the queue
-    __enqueue_in_order -- Queues a lease in order (currently, time of submission)
-    _handle_end_rr -- Code that has to be run when a reservation ends
-    _handle_end_lease -- Code that has to be run at the end of a lease
-    
+    coordinates all the different operations involved in scheduling a lease.    
     """
+    
     def __init__(self, vm_scheduler, preparation_scheduler, slottable):
         """Constructor
         
@@ -469,13 +451,8 @@
         else:
             raise InconsistentLeaseStateError(lease, doing = "scheduling a best-effort lease")
         
-        if isinstance(lease, BestEffortLease):
-            (vmrr, preemptions) = self.vm_scheduler.fit_asap(lease, nexttime, earliest)
-        elif isinstance(lease, ARLease):
-            (vmrr, preemptions) = self.vm_scheduler.fit_exact(lease, preemptible=False, canpreempt=True)
-        elif isinstance(lease, ImmediateLease):
-            (vmrr, preemptions) = self.vm_scheduler.fit_asap(lease, nexttime, earliest, allow_reservation_in_future=False)
-                        
+        (vmrr, preemptions) = self.vm_scheduler.schedule(lease, nextttime, earliest)
+                                
         if len(preemptions) > 0:
             self.logger.info("Must preempt leases %s to make room for lease #%i" % ([l.id for l in preemptions], lease.id))
             for l in preemptions:

Modified: branches/TP2.0/src/haizea/resourcemanager/scheduler/vm_scheduler.py
===================================================================
--- branches/TP2.0/src/haizea/resourcemanager/scheduler/vm_scheduler.py	2009-06-17 15:29:09 UTC (rev 584)
+++ branches/TP2.0/src/haizea/resourcemanager/scheduler/vm_scheduler.py	2009-06-17 16:09:33 UTC (rev 585)
@@ -77,7 +77,15 @@
 
         self.numbesteffortres = 0
 
-    def fit_exact(self, leasereq, preemptible=False, canpreempt=True, avoidpreempt=True):
+    def schedule(self, lease, nexttime, earliest):
+        if isinstance(lease, BestEffortLease):
+            (vmrr, preemptions) = self.vm_scheduler.fit_asap(lease, nexttime, earliest)
+        elif isinstance(lease, ARLease):
+            (vmrr, preemptions) = self.vm_scheduler.fit_exact(lease, preemptible=False, canpreempt=True)
+        elif isinstance(lease, ImmediateLease):
+            (vmrr, preemptions) = self.vm_scheduler.fit_asap(lease, nexttime, earliest, allow_reservation_in_future=False)
+
+    def fit(self, requested_resources, start, end, strictend):
         lease_id = leasereq.id
         start = leasereq.start.requested
         end = leasereq.start.requested + leasereq.duration.requested + self.__estimate_shutdown_time(leasereq)
@@ -556,7 +564,7 @@
     def get_utilization(self, time):
         total = self.slottable.get_total_capacity()
         util = {}
-        reservations = self.slottable.getReservationsAt(time)
+        reservations = self.slottable.get_reservations_at(time)
         for r in reservations:
             for node in r.resources_in_pnode:
                 if isinstance(r, VMResourceReservation):
@@ -913,185 +921,7 @@
             threshold = safe_duration + (min_duration * factor)
             return threshold
 
-    def __find_preemptable_leases(self, mustpreempt, startTime, endTime):
-        def comparepreemptability(rrX, rrY):
-            if rrX.lease.submit_time > rrY.lease.submit_time:
-                return constants.BETTER
-            elif rrX.lease.submit_time < rrY.lease.submit_time:
-                return constants.WORSE
-            else:
-                return constants.EQUAL        
-            
-        def preemptedEnough(amountToPreempt):
-            for node in amountToPreempt:
-                if not amountToPreempt[node].is_zero_or_less():
-                    return False
-            return True
-        
-        # Get allocations at the specified time
-        atstart = set()
-        atmiddle = set()
-        nodes = set(mustpreempt.keys())
-        
-        reservationsAtStart = self.slottable.getReservationsAt(startTime)
-        reservationsAtStart = [r for r in reservationsAtStart if isinstance(r, VMResourceReservation) and r.is_preemptible()
-                        and len(set(r.resources_in_pnode.keys()) & nodes)>0]
-        
-        reservationsAtMiddle = self.slottable.get_reservations_starting_between(startTime, endTime)
-        reservationsAtMiddle = [r for r in reservationsAtMiddle if isinstance(r, VMResourceReservation) and r.is_preemptible()
-                        and len(set(r.resources_in_pnode.keys()) & nodes)>0]
-        
-        reservationsAtStart.sort(comparepreemptability)
-        reservationsAtMiddle.sort(comparepreemptability)
-        
-        amountToPreempt = {}
-        for n in mustpreempt:
-            amountToPreempt[n] = ResourceTuple.copy(mustpreempt[n])
 
-        # First step: CHOOSE RESOURCES TO PREEMPT AT START OF RESERVATION
-        for r in reservationsAtStart:
-            # The following will really only come into play when we have
-            # multiple VMs per node
-            mustpreemptres = False
-            for n in r.resources_in_pnode.keys():
-                # Don't need to preempt if we've already preempted all
-                # the needed resources in node n
-                if amountToPreempt.has_key(n) and not amountToPreempt[n].is_zero_or_less():
-                    amountToPreempt[n].decr(r.resources_in_pnode[n])
-                    mustpreemptres = True
-            if mustpreemptres:
-                atstart.add(r)
-            if preemptedEnough(amountToPreempt):
-                break
-        
-        # Second step: CHOOSE RESOURCES TO PREEMPT DURING RESERVATION
-        if len(reservationsAtMiddle)>0:
-            changepoints = set()
-            for r in reservationsAtMiddle:
-                changepoints.add(r.start)
-            changepoints = list(changepoints)
-            changepoints.sort()        
-            
-            for cp in changepoints:
-                amountToPreempt = {}
-                for n in mustpreempt:
-                    amountToPreempt[n] = ResourceTuple.copy(mustpreempt[n])
-                reservations = [r for r in reservationsAtMiddle 
-                                if r.start <= cp and cp < r.end]
-                for r in reservations:
-                    mustpreemptres = False
-                    for n in r.resources_in_pnode.keys():
-                        if amountToPreempt.has_key(n) and not amountToPreempt[n].is_zero_or_less():
-                            amountToPreempt[n].decr(r.resources_in_pnode[n])
-                            mustpreemptres = True
-                    if mustpreemptres:
-                        atmiddle.add(r)
-                    if preemptedEnough(amountToPreempt):
-                        break
-            
-        self.logger.debug("Preempting leases (at start of reservation): %s" % [r.lease.id for r in atstart])
-        self.logger.debug("Preempting leases (in middle of reservation): %s" % [r.lease.id for r in atmiddle])
-        
-        leases = [r.lease for r in atstart|atmiddle]
-        
-        return leases
-
-
-    def __choose_nodes(self, canfit, start, canpreempt, avoidpreempt):
-        # TODO2: Choose appropriate prioritizing function based on a
-        # config file, instead of hardcoding it)
-        #
-        # TODO3: Basing decisions only on CPU allocations. This is ok for now,
-        # since the memory allocation is proportional to the CPU allocation.
-        # Later on we need to come up with some sort of weighed average.
-        
-        nodes = canfit.keys()
-        
-        # TODO: The deployment module should just provide a list of nodes
-        # it prefers
-        nodeswithimg=[]
-        #self.lease_deployment_type = get_config().get("lease-preparation")
-        #if self.lease_deployment_type == constants.DEPLOYMENT_TRANSFER:
-        #    reusealg = get_config().get("diskimage-reuse")
-        #    if reusealg==constants.REUSE_IMAGECACHES:
-        #        nodeswithimg = self.resourcepool.getNodesWithImgInPool(diskImageID, start)
-
-        # Compares node x and node y. 
-        # Returns "x is ??? than y" (???=BETTER/WORSE/EQUAL)
-        def comparenodes(x, y):
-            hasimgX = x in nodeswithimg
-            hasimgY = y in nodeswithimg
-
-            # First comparison: A node with no preemptible VMs is preferible
-            # to one with preemptible VMs (i.e. we want to avoid preempting)
-            canfitnopreemptionX = canfit[x][0]
-            canfitpreemptionX = canfit[x][1]
-            hasPreemptibleX = canfitpreemptionX > canfitnopreemptionX
-            
-            canfitnopreemptionY = canfit[y][0]
-            canfitpreemptionY = canfit[y][1]
-            hasPreemptibleY = canfitpreemptionY > canfitnopreemptionY
-
-            # TODO: Factor out common code
-            if avoidpreempt:
-                if hasPreemptibleX and not hasPreemptibleY:
-                    return constants.WORSE
-                elif not hasPreemptibleX and hasPreemptibleY:
-                    return constants.BETTER
-                elif not hasPreemptibleX and not hasPreemptibleY:
-                    if hasimgX and not hasimgY: 
-                        return constants.BETTER
-                    elif not hasimgX and hasimgY: 
-                        return constants.WORSE
-                    else:
-                        if canfitnopreemptionX > canfitnopreemptionY: return constants.BETTER
-                        elif canfitnopreemptionX < canfitnopreemptionY: return constants.WORSE
-                        else: return constants.EQUAL
-                elif hasPreemptibleX and hasPreemptibleY:
-                    # If both have (some) preemptible resources, we prefer those
-                    # that involve the less preemptions
-                    preemptX = canfitpreemptionX - canfitnopreemptionX
-                    preemptY = canfitpreemptionY - canfitnopreemptionY
-                    if preemptX < preemptY:
-                        return constants.BETTER
-                    elif preemptX > preemptY:
-                        return constants.WORSE
-                    else:
-                        if hasimgX and not hasimgY: return constants.BETTER
-                        elif not hasimgX and hasimgY: return constants.WORSE
-                        else: return constants.EQUAL
-            elif not avoidpreempt:
-                # First criteria: Can we reuse image?
-                if hasimgX and not hasimgY: 
-                    return constants.BETTER
-                elif not hasimgX and hasimgY: 
-                    return constants.WORSE
-                else:
-                    # Now we just want to avoid preemption
-                    if hasPreemptibleX and not hasPreemptibleY:
-                        return constants.WORSE
-                    elif not hasPreemptibleX and hasPreemptibleY:
-                        return constants.BETTER
-                    elif hasPreemptibleX and hasPreemptibleY:
-                        # If both have (some) preemptible resources, we prefer those
-                        # that involve the less preemptions
-                        preemptX = canfitpreemptionX - canfitnopreemptionX
-                        preemptY = canfitpreemptionY - canfitnopreemptionY
-                        if preemptX < preemptY:
-                            return constants.BETTER
-                        elif preemptX > preemptY:
-                            return constants.WORSE
-                        else:
-                            if hasimgX and not hasimgY: return constants.BETTER
-                            elif not hasimgX and hasimgY: return constants.WORSE
-                            else: return constants.EQUAL
-                    else:
-                        return constants.EQUAL
-        
-        # Order nodes
-        nodes.sort(comparenodes)
-        return nodes        
-
     #-------------------------------------------------------------------#
     #                                                                   #
     #                  SLOT TABLE EVENT HANDLERS                        #



More information about the Haizea-commit mailing list