diff --git a/Makefile.am b/Makefile.am index b1f9e82..d3d5e06 100644 --- a/Makefile.am +++ b/Makefile.am @@ -145,6 +145,7 @@ src_backend_libbackend_la_LDFLAGS = \ # Please keep this in sorted order: src_backend_libbackend_la_SOURCES = \ src/backend/concrete_environment.cc \ + src/backend/concrete_history.cc \ src/backend/dynamic_process.cc \ src/backend/dynamic_request.cc \ src/backend/dynamic_resource.cc \ @@ -154,7 +155,7 @@ src_backend_libbackend_la_SOURCES = \ src/backend/environment.cc \ src/backend/global_preferences.cc \ src/backend/history.cc \ - src/backend/observed_subject.cc \ + src/backend/history_observer.cc \ src/backend/policies_gatekeeper.cc \ src/backend/policy.cc \ src/backend/policy_manager.cc \ @@ -164,7 +165,6 @@ src_backend_libbackend_la_SOURCES = \ src/backend/request.cc \ src/backend/resource.cc \ src/backend/schedulable.cc \ - src/backend/schedulable_queue.cc \ src/backend/scheduler.cc \ src/backend/slice.cc \ src/backend/static_process.cc \ @@ -185,7 +185,7 @@ pkginclude_HEADERS += \ src/backend/environment.hh \ src/backend/global_preferences.hh \ src/backend/history.hh \ - src/backend/observed_subject.hh \ + src/backend/history_observer.hh \ src/backend/plugin.hh \ src/backend/policies_gatekeeper.hh \ src/backend/policy.hh \ @@ -196,7 +196,6 @@ pkginclude_HEADERS += \ src/backend/resource.hh \ src/backend/process.hh \ src/backend/schedulable.hh \ - src/backend/schedulable_queue.hh \ src/backend/scheduler.hh \ src/backend/slice.hh \ src/backend/sub_request.hh \ @@ -207,6 +206,7 @@ pkginclude_HEADERS += \ # They won't be installed for the end-user. noinst_HEADERS += \ src/backend/concrete_environment.hh \ + src/backend/concrete_history.hh \ src/backend/dynamic_process.hh \ src/backend/dynamic_request.hh \ src/backend/dynamic_resource.hh \ diff --git a/src/backend/observed_subject.cc b/src/backend/concrete_history.cc similarity index 51% rename from src/backend/observed_subject.cc rename to src/backend/concrete_history.cc index a55ae5a..eb13bcc 100644 --- a/src/backend/observed_subject.cc +++ b/src/backend/concrete_history.cc @@ -1,4 +1,4 @@ -// src/backend/observedSubject.cc - Copyright 2005, 2006, University +// src/backend/concrete_history.cc - Copyright 2005, 2006, University // of Padova, dept. of Pure and Applied // Mathematics // @@ -18,47 +18,7 @@ // along with SGPEMv2; if not, write to the Free Software // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -#include "observed_subject.hh" -using namespace std; -using namespace sgpem; - - -ObservedSubject::~ObservedSubject() -{} - -/** - Calls update() in each Observer -*/ -void -ObservedSubject::notify() -{ - for(vector::iterator i = _attached.begin(); i < _attached.end(); i++) - (*i)->update(); - -} - -/** - Attachs an Observer to this ObservedSubject. -*/ -void -ObservedSubject::attach(Observer* o) -{ - _attached.push_back(o); -} - -/** - Detachs the observer from this ObservedSubject. -*/ - -bool -ObservedSubject::detach(Observer* o) -{ - vector::iterator i = find(_attached.begin(), _attached.end(), o); - if (i == _attached.end()) - return false; - - _attached.erase(i); // FOUND and POPPED - return true; -} +#include "config.h" +#include "concrete_history.hh" diff --git a/src/backend/concrete_history.hh b/src/backend/concrete_history.hh new file mode 100644 index 0000000..d6e8af6 --- /dev/null +++ b/src/backend/concrete_history.hh @@ -0,0 +1,106 @@ +// src/backend/concrete_history.hh - Copyright 2005, 2006, University +// of Padova, dept. of Pure and Applied +// Mathematics +// +// This file is part of SGPEMv2. +// +// This is free software; you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation; either version 2 of the License, or +// (at your option) any later version. +// +// SGPEMv2 is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with SGPEMv2; if not, write to the Free Software +// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +#ifndef CONCRETE_HISTORY_HH +#define CONCRETE_HISTORY_HH 1 + +#include "config.h" + +#include "concrete_environment.hh" +#include "dynamic_process.hh" +#include "dynamic_request.hh" +#include "dynamic_resource.hh" +#include "dynamic_sub_request.hh" +#include "dynamic_thread.hh" +#include "history.hh" + +#include + +#include +#include +#include +#include + +namespace sgpem +{ + class ConcreteHistory; + + class SG_DLLLOCAL ConcreteHistory : public History + { + public: + typedef const std::pair DynamicResourcePair; + + ConcreteHistory(); + ConcreteHistory(const ConcreteHistory&); + virtual ~ConcreteHistory(); + + virtual void append_new_environment(ConcreteEnvironment* environment); + virtual size_t get_size(); + virtual const ConcreteEnvironment& get_last_environment() const; + virtual const ConcreteEnvironment& get_environment_at() const throw(std::out_of_range); + + virtual void remove(const Resource& resource); + virtual void remove(const Process& process); + virtual void remove(const Thread& thread); + virtual void remove(const Request& request); + virtual void remove(const SubRequest& subrequest); + + + virtual ResourcePair& add_resource(const Glib::ustring& name, + bool preemptable = false, + size_t places = 1, + size_t availability = 0); + + virtual DynamicProcess& add_process(const Glib::ustring& name, + time_t arrival_time, + prio_t base_priority = 0); + + virtual DynamicThread& add_thread(const Glib::ustring& name, + Process& parent, + time_t arrival_time = 0, + prio_t base_priority = 0); + + virtual DynamicRequest& add_request(Thread& owner, + time_t instant); + + virtual DynamicSubRequest& add_subrequest(Request& request, + resource_key_t resource_key, + time_t duration, + size_t places = 1); + + virtual void reset(bool notify = true); + + protected: + typedef std::vector Snapshots; + Snapshots _snapshots; + + virtual void notify_change(); + + private: + // Disable assignment, implement it only if needed + ConcreteHistory& operator=(const ConcreteHistory& op2); + + }; //~ class ConcreteHistory + +}//~ namespace sgpem + +#endif //~ CONCRETE_HISTORY_HH + + diff --git a/src/backend/history.cc b/src/backend/history.cc index 8a5242c..463be75 100644 --- a/src/backend/history.cc +++ b/src/backend/history.cc @@ -21,147 +21,26 @@ #include "config.h" #include "history.hh" -#include "dynamic_process.hh" -#include "dynamic_thread.hh" -// Do not include in header file: -#include "singleton.tcc" -#include "smartp.tcc" - -#include - -using namespace std; +#include using namespace sgpem; -using namespace memory; -// Explicit template instantiation to allow to export symbols from the DSO. -template class SG_DLLEXPORT Singleton; - -// FIXME: These two should disappear!!! -template class SG_DLLEXPORT smart_ptr; -template class SG_DLLEXPORT smart_ptr; - -/** - The constructor sets _total_time_elapsed to -1: this permits to insert the INITIAL STATUS - of the simulation which must begin at instant -1 and live for 1 instant. -*/ -History::History() //private constructor. - : - _total_time_elapsed(-1) -{} - - -/** - Returns a pointer to a copy of the DynamicSchedulable object relative to this instant. - It can be NULL if time is out of range or if there are no running entities in the associated - ReadyQueue -*/ -smart_ptr -History::get_scheduled_at(int time) const +History::~History() { - if (time > _total_time_elapsed || time < 0) //out of range - return smart_ptr(NULL); - - //look for a runing entity - smart_ptr p = get_simulation_status_at(time); - - for (uint i = 0; i < p->size(); i++) - if (p->get_item_at(i).get_state() == DynamicSchedulable::state_running) - { - // Copy the right object - // FIXME: this code has to be reworked (probably ditched by the new ConcreteHistory) - Schedulable* tmp = &p->get_item_at(i); - - DynamicProcess* proc; - DynamicThread* thread; - if((proc = dynamic_cast(tmp)) != NULL) - return smart_ptr(new DynamicProcess(*proc)); - else if((thread = dynamic_cast(tmp)) != NULL) - return smart_ptr(new DynamicThread(*thread)); - else - throw std::bad_cast(); - } - - return smart_ptr(NULL); } -/** - Returns a pointer to a copy of the SimulationStatus object relative to this instant or NULL - if time is out of range. -*/ -smart_ptr -History::get_simulation_status_at(int time) const -{ - if (time > _total_time_elapsed || time < 0) //out of range - return smart_ptr(NULL); - int trascorso = -1; - for(vector::const_iterator i = _slices.begin(); i < _slices.end(); i++) - if (time <= trascorso + i->get_duration()) //FOUND!! - return smart_ptr(new ReadyQueue(*i->get_simulation_status())); - else //Go on... - trascorso += i->get_duration(); - - //never reached if all slices are CONTIGUOUS (ans THIS shoul be!!)!!! - return smart_ptr(NULL); -} - -int -History::get_current_time() const -{ - return _total_time_elapsed; -} - -/** - Appends to the history a SimulationStatus creating a Slice with duration of 1 instant. - Calls the method notify() in quality of ObservedSubject, updating all observers. -*/ void -History::enqueue_slice(const ReadyQueue& status) +History::attach(HistoryObserver& observer) { - if(_slices.size() == 0) - { - _slices.push_back(Slice(-1, 1, status)); - _total_time_elapsed++; - notify(); - return; - } - - //check the last slice - Slice& last = _slices[_slices.size()-1]; - if (last.get_simulation_status()->has_same_objects(status)) //increments the duration by ONE unit - { - last.set_duration(last.get_duration() + 1); - } - else //insert a new slice CONTIGUOUS to the last one - { - _slices.push_back(Slice(last.get_started_at() + last.get_duration(), 1, status)); - } - _total_time_elapsed++; //one instant is passed... - notify(); + _observers.push_back(&observer); } -/** - Removes all the informations about the simulation following the specified instant. - - Ex. truncate_at(0); removes all scheduled slices - Ex. truncate_at(-1); removes all scheduled slices and the initial status -*/ + void -History::truncate_at(int instant) +History::detach(const HistoryObserver& observer) { - vector::iterator i = _slices.begin(); - //reach the instant - while (i != _slices.end()) - if (i->get_started_at() < instant) - i++; - else - { - //replaces the current vector with the "trimmed" one. - _slices = vector(_slices.begin(), i); - _total_time_elapsed = instant; - break; - } - notify(); + _observers.erase(std::find(_observers.begin(), + _observers.end(), + &observer)); } - diff --git a/src/backend/history.hh b/src/backend/history.hh index 2765476..69bfbfd 100644 --- a/src/backend/history.hh +++ b/src/backend/history.hh @@ -23,21 +23,17 @@ #include "config.h" +#include "environment.hh" + +#include + +#include +#include #include -#include -#include "slice.hh" -#include "observed_subject.hh" -#include "ready_queue.hh" -#include "dynamic_schedulable.hh" -#include "smartp.hh" - -// Do not include complete template definition here: -#include "singleton.hh" namespace sgpem { - /** \brief Manages the history of the simulation Manages the history of the simulation from the instant 0 to the current time, @@ -46,59 +42,73 @@ namespace sgpem In a future iteration it will be possible to revert the entire simulation to a state present in the history ("undo operation") - */ class History; - class SG_DLLEXPORT History : public Singleton, public ObservedSubject + // Forward declarations: + class HistoryObserver; + class Resource; + class Process; + class Thread; + class Request; + class SubRequest; + + class SG_DLLEXPORT History { - friend class Singleton; - public: - /** - Gets the \ref Schedulable object running at the specified time. - \param time The inquired time instant. - \return The Schedulable object running at the given time. - */ - virtual memory::smart_ptr get_scheduled_at(int time) const; + typedef unsigned int size_t; + typedef unsigned int time_t; + typedef int prio_t; + typedef int resource_key_t; + typedef const std::pair ResourcePair; - /** - Gets the status of simulation at the specified time. - \param time The inquired time instant. - \return The list of Schedulable status objects at the specified time. - */ - virtual memory::smart_ptr get_simulation_status_at(int time) const; + virtual ~History() = 0; + + virtual size_t get_size() = 0; + virtual const Environment& get_last_environment() const = 0; + virtual const Environment& get_environment_at() const throw(std::out_of_range) = 0; + + virtual void remove(const Resource& resource) = 0; + virtual void remove(const Process& process) = 0; + virtual void remove(const Thread& thread) = 0; + virtual void remove(const Request& request) = 0; + virtual void remove(const SubRequest& subrequest) = 0; - /** - Gets the current time. - \return The current history time. - */ - virtual int get_current_time() const; - /** - Sets the status of simulation at the current time. - \param status The list of \ref Schedulable status objects at the current time. - */ - virtual void enqueue_slice(const sgpem::ReadyQueue& status); + virtual ResourcePair& add_resource(const Glib::ustring& name, + bool preemptable = false, + size_t places = 1, + size_t availability = 0) = 0; - /** - Remove all data in History following the specified time. - \param instant Desired cutting time. - */ - virtual void truncate_at(int instant); + virtual Process& add_process(const Glib::ustring& name, + time_t arrival_time, + prio_t base_priority = 0) = 0; - protected: - History(); //private constructor. - History(const History&); - History& operator=(const History&); + virtual Thread& add_thread(const Glib::ustring& name, + Process& parent, + time_t arrival_time = 0, + prio_t base_priority = 0) = 0; - private: - int _total_time_elapsed; - std::vector _slices; - }; + virtual Request& add_request(Thread& owner, + time_t instant) = 0; + + virtual SubRequest& add_subrequest(Request& request, + resource_key_t resource_key, + time_t duration, + size_t places = 1) = 0; + + + virtual void attach(HistoryObserver& observer); + virtual void detach(const HistoryObserver& observer); + + protected: + typedef std::vector RegisteredObservers; + RegisteredObservers _observers; + + virtual void notify_change() = 0; + + }; //~ class History }//~ namespace sgpem -#endif //HISTORY_H - - +#endif //~ HISTORY_HH diff --git a/src/backend/history_observer.cc b/src/backend/history_observer.cc new file mode 100644 index 0000000..9ce105f --- /dev/null +++ b/src/backend/history_observer.cc @@ -0,0 +1,25 @@ +// src/backend/history_observer.cc - Copyright 2005, 2006, University +// of Padova, dept. of Pure and Applied +// Mathematics +// +// This file is part of SGPEMv2. +// +// This is free software; you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation; either version 2 of the License, or +// (at your option) any later version. +// +// SGPEMv2 is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with SGPEMv2; if not, write to the Free Software +// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + +#include "history_observer.hh" + +sgpem::HistoryObserver::~HistoryObserver() {} + +// Pure abstract class. Nothing else to put here. diff --git a/src/backend/slice.cc b/src/backend/history_observer.hh similarity index 61% rename from src/backend/slice.cc rename to src/backend/history_observer.hh index b1e1254..a9f0df4 100644 --- a/src/backend/slice.cc +++ b/src/backend/history_observer.hh @@ -1,4 +1,4 @@ -// src/backend/silce.cc - Copyright 2005, 2006, University +// src/backend/history_observer.hh - Copyright 2005, 2006, University // of Padova, dept. of Pure and Applied // Mathematics // @@ -18,36 +18,26 @@ // along with SGPEMv2; if not, write to the Free Software // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA -#include "slice.hh" -using namespace sgpem; -using namespace std; +#ifndef HISTORY_OBSERVER_HH +#define HISTORY_OBSERVER_HH 1 +#include "config.h" -Slice::Slice(const int& start, const int& duration, const ReadyQueue& status) - : _ref(status), _started_at(start), _duration(duration) -{} - -const ReadyQueue* -Slice::get_simulation_status() const +namespace sgpem { - return &_ref; -} + class History; + class HistoryObserver; -int -Slice::get_started_at() const -{ - return _started_at; -} + class SG_DLLEXPORT HistoryObserver + { + public: + virtual void update(History& changed_history) = 0; + virtual ~HistoryObserver(); -int -Slice::get_duration() const -{ - return _duration; -} + }; // class HistoryObserver + +}//~ namespace sgpem + +#endif //HISTORY_OBSERVER_H -void -Slice::set_duration(const int& i) -{ - _duration = i; -} diff --git a/src/backend/observed_subject.hh b/src/backend/observed_subject.hh deleted file mode 100644 index d49fd69..0000000 --- a/src/backend/observed_subject.hh +++ /dev/null @@ -1,75 +0,0 @@ -// src/backend/observedSubject.hh - Copyright 2005, 2006, University -// of Padova, dept. of Pure and Applied -// Mathematics -// -// This file is part of SGPEMv2. -// -// This is free software; you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation; either version 2 of the License, or -// (at your option) any later version. -// -// SGPEMv2 is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with SGPEMv2; if not, write to the Free Software -// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -#ifndef OBSERVEDSUBJECT_HH -#define OBSERVEDSUBJECT_HH 1 - -#include "config.h" - -#include -#include - -#include "../observer.hh" - -namespace sgpem -{ - - class ObservedSubject; - - /** \brief Represents an observed entity. - - Abstract class which represents an observed entity. It calls Update() in all Observer objects - which are attached to it. See the "Observer Pattern" for more informations. - */ - class SG_DLLEXPORT ObservedSubject - { - public: - virtual ~ObservedSubject() = 0; - - /** - This method calls Update() on each attached Observer. It should be called when the internal state - of the ObservedSubject is changed and Observers have to be updated. - */ - void notify(); - - - /** - \brief Adds an Observer object to the internal list. - */ - void attach(sgpem::Observer*); - - - /** - \brief Removes an Observer object from the internal list. - - \returns TRUE if the Observer object has been previously attached (is found in the list); - \returns FALSE otherwise. - */ - bool detach(sgpem::Observer*); - - private: - std::vector _attached; - }; - -} //~ namespace sgpem - - -#endif - diff --git a/src/backend/policy.cc b/src/backend/policy.cc index b13babb..3315676 100644 --- a/src/backend/policy.cc +++ b/src/backend/policy.cc @@ -21,7 +21,6 @@ #include "policy.hh" using namespace std; using namespace sgpem; -using namespace memory; Policy::~Policy() {} diff --git a/src/backend/ready_queue.cc b/src/backend/ready_queue.cc index 7624067..bbae6ab 100644 --- a/src/backend/ready_queue.cc +++ b/src/backend/ready_queue.cc @@ -29,15 +29,15 @@ void ReadyQueue::swap(position a, position b) throw (std::out_of_range) { - size_t size = _scheds.size(); - if(a > size || b > size) - throw std::out_of_range(_("Trying to access a Schedulable " - "with an index outside of the " - "queue limits.")); if(a == b) return; - - Schedulable* temp = _scheds[a]; - _scheds[a] = _scheds[b]; + + // Usage of "at()" isn't casual: + // at() checks indexes, "[]" doesn't. + // Once we've done the check once, we + // can assume it's safe to use "[]"; + // this for performance reasons. + Schedulable* temp = _scheds.at(a); + _scheds[a] = _scheds.at(b); _scheds[b] = temp; } @@ -53,11 +53,8 @@ sgpem::Schedulable& ReadyQueue::get_item_at(position index) throw (std::out_of_range) { - if(index > size()) - throw std::out_of_range(_("Trying to access a Schedulable " - "with an index outside of the " - "queue limits.")); - return *(_scheds[index]); + // Checks index access + return *_scheds.at(index); } diff --git a/src/backend/scheduler.cc b/src/backend/scheduler.cc index 094b35b..6843c78 100644 --- a/src/backend/scheduler.cc +++ b/src/backend/scheduler.cc @@ -30,7 +30,6 @@ #include using namespace std; using namespace sgpem; -using namespace memory; // Explicit template instantiation to allow to export symbols from the DSO. template class SG_DLLEXPORT Singleton; diff --git a/src/backend/scheduler.hh b/src/backend/scheduler.hh index 7570b27..291e970 100644 --- a/src/backend/scheduler.hh +++ b/src/backend/scheduler.hh @@ -32,7 +32,6 @@ namespace sgpem #include #include -#include "observed_subject.hh" #include "history.hh" #include "ready_queue.hh" #include "user_interrupt_exception.hh" diff --git a/src/backend/slice.hh b/src/backend/slice.hh deleted file mode 100644 index 7b89ed3..0000000 --- a/src/backend/slice.hh +++ /dev/null @@ -1,84 +0,0 @@ -// src/backend/slice.hh - Copyright 2005, 2006, University -// of Padova, dept. of Pure and Applied -// Mathematics -// -// This file is part of SGPEMv2. -// -// This is free software; you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation; either version 2 of the License, or -// (at your option) any later version. -// -// SGPEMv2 is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with SGPEMv2; if not, write to the Free Software -// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - -#ifndef SLICE_HH -#define SLICE_HH 1 - -#include "config.h" - -#include "ready_queue.hh" - -namespace sgpem -{ - class Slice; - - /** \brief Represents a slice of time during which some characteristic of the state of the simulation are constant - - Represents a slice of time during which some characteristic of the state of the simulation are constant. - It holds a \ref SimulationStatus object which can be accessed through getSimulationStatus() - - */ - - class SG_DLLEXPORT Slice - { - public: - /** - Constructor for Slice. - \param start The Slice's starting time. - \param duration Time length of Slice. - \param status Photoshot of all \ref Schedulable during this Slice. - */ - Slice(const int& start, const int& duration, const ReadyQueue& status); - - /** - Gets a constant reference to the \ref ReadyQueue object for this Slice. - \return The reference (constant) to the ReadyQueue object for this Slice. - */ - const ReadyQueue* get_simulation_status() const; - - - /** - Gets starting time of this Slice. - \return The starting time. - */ - int get_started_at() const; - - /** - Gets duration of this Slice. - \return The duration time. - */ - int get_duration() const; - - /** - Sets duration of this Slice. - \param duration The desired duration time. - */ - void set_duration(const int& duration); - - private: - ReadyQueue _ref; - int _started_at; - int _duration; - }; - -} //~ namespace sgpem - -#endif -