Main Page | Namespace List | Class Hierarchy | Class List | File List | Namespace Members | Class Members | File Members | Related Pages

PartitionPolicyImpl.cc

Go to the documentation of this file.
00001 /*
00002  * PartitionPolicyImpl.cc
00003  *
00004  * Copyright (c) 2003, 2004 The University of Utah and the Flux Group.
00005  * All rights reserved.
00006  *
00007  * This file is licensed under the terms of the GNU Public License.  
00008  * See the file "license.terms" for restrictions on redistribution 
00009  * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
00010  */
00011 
00012 /**
00013  * @file PartitionPolicyImpl.cc
00014  *
00015  * Implementation of the PartitionPolicyImpl class.
00016  */
00017 
00018 #include "config.h"
00019 
00020 #include <iostream>
00021 #include <assert_pp.h>
00022 
00023 #include "StubRealTimeTask.hh"
00024 #include "PartitionPolicyImpl.hh"
00025 
00026 using namespace std;
00027 
00028 PartitionPolicyImpl::PartitionPolicyImpl(const char *name) :
00029     pp_Name(name)
00030 {
00031     require(name != NULL);
00032     
00033     lnNewList((struct lnMinList *)&this->pp_List);
00034 }
00035 
00036 PartitionPolicyImpl::~PartitionPolicyImpl()
00037 {
00038 }
00039 
00040 char *PartitionPolicyImpl::Name(void)
00041     throw (CORBA::SystemException)
00042 {
00043     CORBA::String_var retval;
00044 
00045     retval = this->pp_Name;
00046     return( retval._retn() );
00047 }
00048 
00049 CORBA::Float PartitionPolicyImpl::GetMaxCPUAllocation(void)
00050     throw (CORBA::SystemException)
00051 {
00052     CORBA::Float retval;
00053 
00054     retval = this->pp_MaxUsedCPU;
00055     return( retval );
00056 }
00057 
00058 void PartitionPolicyImpl::SetMaxCPUAllocation(CORBA::Float value)
00059     throw (CORBA::SystemException)
00060 {
00061     if( (value < BrokerPolicies::PartitionPolicy::CPU_ALLOCATION_MIN) ||
00062         (value > BrokerPolicies::PartitionPolicy::CPU_ALLOCATION_MAX) )
00063     {
00064         throw CORBA::BAD_PARAM();
00065     }
00066 
00067     this->pp_MaxUsedCPU = value;
00068 }
00069 
00070 void PartitionPolicyImpl::AddTask(Broker::Task_ptr task,
00071                                   const Broker::ScheduleParameters &sp)
00072     throw (CORBA::SystemException,
00073            Broker::DuplicateScheduleParameter,
00074            Broker::InvalidScheduleParameter,
00075            Broker::MissingScheduleParameter)
00076 {
00077     Broker::RealTimeTask_ptr rtt;
00078     
00079     /* Check inputs, */
00080     if( CORBA::is_nil(task) )
00081     {
00082         throw CORBA::BAD_PARAM();
00083     }
00084 
00085     /* ... make sure our internal list is sane, and */
00086     this->RepairTaskList();
00087     
00088     /* ... try to add the task. */
00089     rtt = Broker::RealTimeTask::_narrow(task);
00090     if( !CORBA::is_nil(rtt) )
00091     {
00092         /* Make sure there is a default policy and then */
00093         if( !CORBA::is_nil(this->pp_DefaultPolicy.in()) )
00094         {
00095             try
00096             {
00097                 this->pp_DefaultPolicy->AddTask(task, sp);
00098             }
00099             catch(const Broker::DuplicateScheduleParameter &e)
00100             {
00101                 throw e;
00102             }
00103             catch(const Broker::InvalidScheduleParameter &e)
00104             {
00105                 throw e;
00106             }
00107             catch(const Broker::MissingScheduleParameter &e)
00108             {
00109                 throw e;
00110             }
00111         }
00112 
00113         /* ... add it to our own list. */
00114         struct TaskData *td;
00115         
00116         td = new TaskData();
00117         td->td_Task = Broker::RealTimeTask::_duplicate(rtt);
00118         td->td_ScheduleParameters = new Broker::ScheduleParameters(sp);
00119         td->td_Policy = Broker::Policy::
00120             _duplicate(this->pp_DefaultPolicy.in());
00121         lnAddTail(&this->pp_List, &td->td_Link);
00122     }
00123 }
00124 
00125 void PartitionPolicyImpl::RemoveTask(Broker::Task_ptr task)
00126     throw (CORBA::SystemException)
00127 {
00128     Broker::RealTimeTask_var rtt;
00129     struct TaskData *td;
00130     
00131     this->RepairTaskList();
00132     
00133     /* Find the task, */
00134     try
00135     {
00136         rtt = Broker::RealTimeTask::_narrow(task);
00137         if( (td = this->FindTaskData(rtt.in())) == NULL )
00138         {
00139             throw CORBA::BAD_PARAM();
00140         }
00141     }
00142     catch(const CORBA::TRANSIENT &e)
00143     {
00144         throw CORBA::BAD_PARAM();
00145     }
00146     
00147     /* ... remove the node, and */
00148     lnRemove((struct lnMinNode *)&td->td_Link);
00149     if( !CORBA::is_nil(td->td_Policy.in()) )
00150     {
00151         td->td_Policy->RemoveTask(task);
00152     }
00153     /* ... delete it. */
00154     delete td;
00155 }
00156 
00157 void PartitionPolicyImpl::Activate(const Broker::TaskList &tl)
00158     throw (CORBA::SystemException)
00159 {
00160     /** @todo implement */
00161 }
00162 
00163 void PartitionPolicyImpl::Deactivate(void)
00164     throw (CORBA::SystemException)
00165 {
00166     /** @todo implement */
00167 }
00168 
00169 void PartitionPolicyImpl::DefaultPolicy(Broker::Policy_ptr bp)
00170     throw (CORBA::SystemException)
00171 {
00172     this->pp_DefaultPolicy = Broker::Policy::_duplicate(bp);
00173 }
00174 
00175 Broker::Policy_ptr PartitionPolicyImpl::DefaultPolicy(void)
00176     throw (CORBA::SystemException)
00177 {
00178     Broker::Policy_var retval;
00179 
00180     retval = this->pp_DefaultPolicy;
00181     return( retval._retn() );
00182 }
00183 
00184 Broker::TaskList *PartitionPolicyImpl::GetTaskList(void)
00185     throw (CORBA::SystemException)
00186 {
00187     Broker::TaskList_var retval;
00188     struct TaskData *tp;
00189     unsigned int lpc = 0;
00190     
00191     retval = new Broker::TaskList();
00192     retval->length(lnCountNodes((struct lnMinList *)&this->pp_List));
00193     tp = (struct TaskData *)this->pp_List.lh_Head;
00194     while( tp->td_Link.ln_Succ != NULL )
00195     {
00196         (*retval)[lpc] = Broker::Task::_duplicate(tp->td_Task.in());
00197         lpc += 1;
00198         tp = (struct TaskData *)tp->td_Link.ln_Succ;
00199     }
00200     return( retval._retn() );
00201 }
00202 
00203 void PartitionPolicyImpl::SetTaskPolicy(Broker::Task_ptr task,
00204                                         Broker::Policy_ptr policy)
00205     throw (CORBA::SystemException)
00206 {
00207     Broker::RealTimeTask_var rtt;
00208     struct TaskData *td;
00209 
00210     rtt = Broker::RealTimeTask::_narrow(task);
00211     if( CORBA::is_nil(rtt.in()) )
00212     {
00213         throw CORBA::BAD_PARAM();
00214     }
00215 
00216     /* Find the task, */
00217     if( (td = this->FindTaskData(rtt.in())) == NULL )
00218     {
00219         throw CORBA::BAD_PARAM();
00220     }
00221 
00222     /* ... remove it from the old, and */
00223     if( !CORBA::is_nil(td->td_Policy.in()) )
00224     {
00225         td->td_Policy->RemoveTask(task);
00226     }
00227     
00228     /* ... add it to the new. */
00229     td->td_Policy = Broker::Policy::_duplicate(policy);
00230 
00231     if( !CORBA::is_nil(td->td_Policy.in()) )
00232     {
00233         td->td_Policy->AddTask(task, td->td_ScheduleParameters);
00234     }
00235 }
00236 
00237 Broker::Policy_ptr PartitionPolicyImpl::GetTaskPolicy(Broker::Task_ptr task)
00238     throw (CORBA::SystemException)
00239 {
00240     Broker::RealTimeTask_var rtt;
00241     Broker::Policy_var retval;
00242     struct TaskData *td;
00243 
00244     rtt = Broker::RealTimeTask::_narrow(task);
00245     if( CORBA::is_nil(rtt.in()) )
00246     {
00247         throw CORBA::BAD_PARAM();
00248     }
00249     if( (td = this->FindTaskData(rtt.in())) == NULL )
00250     {
00251         throw CORBA::BAD_PARAM();
00252     }
00253 
00254     retval = td->td_Policy;
00255     
00256     return( retval._retn() );
00257 }
00258 
00259 void PartitionPolicyImpl::RepairTaskList(void)
00260 {
00261     struct TaskData *curr, *succ;
00262     
00263     curr = (struct TaskData *)this->pp_List.lh_Head;
00264     while( curr->td_Link.ln_Succ != NULL )
00265     {
00266         succ = (struct TaskData *)curr->td_Link.ln_Succ;
00267         try
00268         {
00269             CORBA::String_var name = curr->td_Task->Name();
00270         }
00271         catch(const CORBA::TRANSIENT &e)
00272         {
00273             try
00274             {
00275                 curr->td_Policy->RemoveTask(curr->td_Task.in());
00276             }
00277             catch(const CORBA::BAD_PARAM &e)
00278             {
00279                 /* Ignore... */
00280             }
00281             catch(const CORBA::SystemException &e)
00282             {
00283                 cerr << "Error while repairing: "
00284                      << e
00285                      << " file: "
00286                      << __FILE__
00287                      << " line: "
00288                      << __LINE__
00289                      << endl;
00290             }
00291             lnRemove((struct lnMinNode *)&curr->td_Link);
00292             delete curr;
00293         }
00294         curr = succ;
00295     }
00296 }
00297 
00298 struct PartitionPolicyImpl::TaskData *
00299 PartitionPolicyImpl::FindTaskData(Broker::RealTimeTask_ptr task)
00300 {
00301     struct TaskData *curr, *retval = NULL;
00302 
00303     require(task != NULL);
00304     
00305     curr = (struct TaskData *)this->pp_List.lh_Head;
00306     while( (retval == NULL) && (curr->td_Link.ln_Succ != NULL) )
00307     {
00308         if( task->_is_equivalent(curr->td_Task.in()) )
00309         {
00310             retval = curr;
00311         }
00312         curr = (struct TaskData *)curr->td_Link.ln_Succ;
00313     }
00314 
00315     return( retval );
00316 }
00317 
00318 Broker::CPUReserve
00319 PartitionPolicyImpl::ChangeTaskCPU(Broker::RealTimeTask_ptr task,
00320                                    const Broker::CPUReserve &advice)
00321     throw (CORBA::SystemException, Broker::InvalidState)
00322 {
00323     Broker::CPUReserve retval = advice;
00324     struct TaskData *td;
00325 
00326     require(task != NULL);
00327 
00328     /* Try to pass the request on to the real policy. */
00329     if( (td = this->FindTaskData(task)) != NULL )
00330     {
00331         if( !CORBA::is_nil(td->td_Policy.in()) )
00332         {
00333             retval = td->td_Policy->ChangeTaskCPU(task, advice);
00334         }
00335         else
00336         {
00337             retval.Compute = 0;
00338         }
00339     }
00340     else
00341     {
00342         throw Broker::InvalidState("AddTask must be called first");
00343     }
00344     return retval;
00345 }

Generated on Fri Oct 22 07:50:24 2004 for CPU Broker by  doxygen 1.3.9.1