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

ManagerImpl.cc

Go to the documentation of this file.
00001 /*
00002  * ManagerImpl.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 ManagerImpl.cc
00014  *
00015  * Implementation of the ManagerImpl class.
00016  */
00017 
00018 #include "config.h"
00019 
00020 #include <iostream>
00021 
00022 #include <assert_pp.h>
00023 #include <instrumentation.h>
00024 
00025 #include "ManagerImpl.hh"
00026 
00027 using namespace std;
00028 
00029 #define INSTR_manager_change_cpu LRTIME_INSTR
00030 #define INSTR_manager_change_cpu_data "manager_change_cpu", "The wall clock time needed to run ChangeTaskCPU"
00031 
00032 #if defined(INSTR_manager_change_cpu_data)
00033 static struct iPoint INSTR_manager_change_cpu_point = {
00034     INSTR_manager_change_cpu_data
00035 };
00036 #endif
00037 
00038 ManagerImpl::ManagerImpl(const char *name)
00039 {
00040     static int initialized = 0;
00041 
00042     if( !initialized )
00043     {
00044         atexit(iPrintPointsAtExit);
00045         initialized = 1;
00046     }
00047     lnNewList(&this->mi_Tasks);
00048 }
00049 
00050 ManagerImpl::~ManagerImpl()
00051 {
00052 }
00053 
00054 void ManagerImpl::RepairTaskList(void)
00055 {
00056     struct TaskNode *curr, *next;
00057 
00058     curr = (struct TaskNode *)this->mi_Tasks.lh_Head;
00059     while( curr->tn_Link.ln_Succ != NULL )
00060     {
00061         Broker::Task_ptr task = curr->tn_Task.in();
00062         
00063         next = (struct TaskNode *)curr->tn_Link.ln_Succ;
00064         
00065         try
00066         {
00067             CORBA::String_var name;
00068 
00069             /* ... do an RPC, and */
00070             name = task->Name();
00071             /* ... move to the next node. */
00072         }
00073         catch(const CORBA::TRANSIENT &e)
00074         {
00075             /* Oops, task is toast, try to tell the policy and */
00076             if( !CORBA::is_nil(this->mi_CurrentPolicy.in()) )
00077             {
00078                 try
00079                 {
00080                     this->mi_CurrentPolicy->RemoveTask(task);
00081                 }
00082                 catch(const CORBA::BAD_PARAM &e)
00083                 {
00084                     /* Ignore... */
00085                 }
00086                 catch(const CORBA::SystemException &e)
00087                 {
00088                     cerr << "Error while repairing: "
00089                          << e
00090                          << " file: "
00091                          << __FILE__
00092                          << " line: "
00093                          << __LINE__
00094                          << endl;
00095                 }
00096             }
00097             /* ... then remove it. */
00098             lnRemove(&curr->tn_Link);
00099             task = Broker::Task::_nil(); /* 'task' is dead after removal. */
00100 
00101             delete curr;
00102             curr = NULL;
00103         }
00104         
00105         curr = next;
00106     }
00107 }
00108 
00109 struct ManagerImpl::TaskNode *ManagerImpl::FindTask(Broker::Task_ptr task)
00110 {
00111     struct TaskNode *curr, *retval = NULL;
00112 
00113     curr = (struct TaskNode *)this->mi_Tasks.lh_Head;
00114     while( (curr->tn_Link.ln_Succ != NULL) && (retval == NULL) )
00115     {
00116         if( curr->tn_Task->_is_equivalent(task) )
00117         {
00118             retval = curr;
00119         }
00120         curr = (struct TaskNode *)curr->tn_Link.ln_Succ;
00121     }
00122     return( retval );
00123 }
00124 
00125 Broker::Policy_ptr ManagerImpl::CurrentPolicy(void)
00126     throw (CORBA::SystemException)
00127 {
00128     Broker::Policy_var retval;
00129 
00130     retval = this->mi_CurrentPolicy;
00131     return( retval._retn() );
00132 }
00133 
00134 void ManagerImpl::CurrentPolicy(Broker::Policy_ptr policy)
00135     throw (CORBA::SystemException)
00136 {
00137     if( !CORBA::is_nil(this->mi_CurrentPolicy.in()) )
00138     {
00139         struct TaskNode *tn;
00140 
00141         tn = (struct TaskNode *)this->mi_Tasks.lh_Head;
00142         while( tn->tn_Link.ln_Succ != NULL )
00143         {
00144             this->mi_CurrentPolicy->RemoveTask(tn->tn_Task.in());
00145             tn = (struct TaskNode *)tn->tn_Link.ln_Succ;
00146         }
00147     }
00148     this->mi_CurrentPolicy = Broker::Policy::_duplicate(policy);
00149     if( !CORBA::is_nil(this->mi_CurrentPolicy.in()) )
00150     {
00151         struct TaskNode *tn;
00152 
00153         tn = (struct TaskNode *)this->mi_Tasks.lh_Head;
00154         while( tn->tn_Link.ln_Succ != NULL )
00155         {
00156             this->mi_CurrentPolicy->AddTask(tn->tn_Task.in(),
00157                                             tn->tn_ScheduleParameters);
00158             tn = (struct TaskNode *)tn->tn_Link.ln_Succ;
00159         }
00160     }
00161 }
00162 
00163 void ManagerImpl::AddTask(Broker::Task_ptr task,
00164                           const Broker::ScheduleParameters &sp)
00165     throw (CORBA::SystemException,
00166            Broker::DuplicateScheduleParameter,
00167            Broker::InvalidScheduleParameter,
00168            Broker::MissingScheduleParameter)
00169 {
00170     if( CORBA::is_nil(task) )
00171     {
00172         throw CORBA::BAD_PARAM();
00173     }
00174 
00175     /* Make sure our list is sane and */
00176     this->RepairTaskList();
00177 
00178     /* ... the task is not already in the list. */
00179     if( this->FindTask(task) != NULL )
00180     {
00181         throw CORBA::BAD_PARAM();
00182     }
00183 
00184     /* Make a new node, */
00185     auto_ptr<struct TaskNode> tn(new TaskNode());
00186 
00187     /* ... fill out the object, */
00188     tn->tn_Task = Broker::Task::_duplicate(task);
00189     tn->tn_ScheduleParameters = new Broker::ScheduleParameters(sp);
00190 
00191     /* ... set things in motion, and */
00192     if( !CORBA::is_nil(this->mi_CurrentPolicy.in()) )
00193     {
00194         this->mi_CurrentPolicy->AddTask(task, sp);
00195     }
00196     tn->tn_Task->BeginCPUScheduling(sp);
00197     tn->tn_Task->SetManager(this->_this());
00198     
00199     /* ... transfer ownership of 'tn' from this frame to the list. */
00200     lnAddTail(&this->mi_Tasks, &(tn.release())->tn_Link);
00201 }
00202 
00203 void ManagerImpl::RemoveTask(Broker::Task_ptr task)
00204     throw (CORBA::SystemException)
00205 {
00206     struct TaskNode *tn;
00207     
00208     if( CORBA::is_nil(task) )
00209     {
00210         throw CORBA::BAD_PARAM();
00211     }
00212 
00213     /* Find the task, */
00214     if( (tn = this->FindTask(task)) == NULL )
00215     {
00216         throw CORBA::BAD_PARAM();
00217     }
00218 
00219     /* ... remove it from our list, and */
00220     lnRemove(&tn->tn_Link);
00221 
00222     /* ... tell the policy. */
00223     if( !CORBA::is_nil(this->mi_CurrentPolicy.in()) )
00224     {
00225         this->mi_CurrentPolicy->RemoveTask(task);
00226     }
00227     
00228     delete tn;
00229 }
00230 
00231 Broker::TaskList *ManagerImpl::GetTaskList(void)
00232     throw (CORBA::SystemException)
00233 {
00234     Broker::TaskList_var retval;
00235     unsigned int lpc = 0;
00236     struct TaskNode *tn;
00237 
00238     retval = new Broker::TaskList();
00239     retval->length(lnCountNodes(&this->mi_Tasks));
00240     tn = (struct TaskNode *)this->mi_Tasks.lh_Head;
00241     while( tn->tn_Link.ln_Succ != NULL )
00242     {
00243         (*retval)[lpc] = Broker::Task::_duplicate(tn->tn_Task.in());
00244         lpc += 1;
00245         tn = (struct TaskNode *)tn->tn_Link.ln_Succ;
00246     }
00247     return( retval._retn() );
00248 }
00249 
00250 Broker::CPUReserve ManagerImpl::ChangeTaskCPU(Broker::RealTimeTask_ptr task,
00251                                               const Broker::CPUReserve &advice)
00252     throw (CORBA::SystemException, Broker::InvalidState)
00253 {
00254     if( CORBA::is_nil(task) )
00255     {
00256         throw CORBA::BAD_PARAM();
00257     }
00258     
00259     if( !CORBA::is_nil(this->mi_CurrentPolicy.in()) )
00260     {
00261         /* Have a policy, just pass it on. */
00262         return this->mi_CurrentPolicy->ChangeTaskCPU(task, advice);
00263     }
00264     else
00265     {
00266         Broker::CPUReserve retval;
00267 
00268         retval = advice;
00269         retval.Compute = 0;
00270         return retval;
00271     }
00272 }
00273 
00274 Broker::Task_ptr ManagerImpl::ResolveTask(CORBA::ORB_ptr orb,
00275                                           Broker::TaskList &tl,
00276                                           const char *name)
00277     throw (CORBA::SystemException)
00278 {
00279     Broker::Task_var retval;
00280     unsigned int lpc;
00281 
00282     require(!CORBA::is_nil(orb));
00283     require(name != NULL);
00284 
00285     /* First try finding the task, by name, in the list. */
00286     for( lpc = 0; (lpc < tl.length()) && CORBA::is_nil(retval.in()); lpc++ )
00287     {
00288         try
00289         {
00290             CORBA::String_var task_name;
00291             
00292             task_name = tl[lpc]->Name();
00293             if( strcmp(task_name.in(), name) == 0 )
00294             {
00295                 retval = Broker::Task::_duplicate(tl[lpc]);
00296             }
00297         }
00298         catch(const CORBA::SystemException &e)
00299         {
00300             /* ... */
00301         }
00302     }
00303     if( CORBA::is_nil(retval.in()) )
00304     {
00305         CORBA::Object_var obj;
00306 
00307         /* No luck finding it in the list, check if it is an IOR. */
00308         try
00309         {
00310             obj = orb->string_to_object(name);
00311         }
00312         catch(const CORBA::SystemException &e)
00313         {
00314             throw CORBA::BAD_PARAM();
00315         }
00316         retval = Broker::Task::_narrow(obj.in());
00317         if( CORBA::is_nil(retval.in()) )
00318         {
00319             throw CORBA::BAD_PARAM();
00320         }
00321     }
00322     return( retval._retn() );
00323 }

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