Wiselib
|
00001 /*************************************************************************** 00002 ** This file is part of the generic algorithm library Wiselib. ** 00003 ** Copyright (C) 2008,2009 by the Wisebed (www.wisebed.eu) project. ** 00004 ** ** 00005 ** The Wiselib is free software: you can redistribute it and/or modify ** 00006 ** it under the terms of the GNU Lesser General Public License as ** 00007 ** published by the Free Software Foundation, either version 3 of the ** 00008 ** License, or (at your option) any later version. ** 00009 ** ** 00010 ** The Wiselib is distributed in the hope that it will be useful, ** 00011 ** but WITHOUT ANY WARRANTY; without even the implied warranty of ** 00012 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ** 00013 ** GNU Lesser General Public License for more details. ** 00014 ** ** 00015 ** You should have received a copy of the GNU Lesser General Public ** 00016 ** License along with the Wiselib. ** 00017 ** If not, see <http://www.gnu.org/licenses/>. ** 00018 ***************************************************************************/ 00019 #ifndef __UTIL_METRICS_ENERGY_CONSUMPTION_RADIO_H 00020 #define __UTIL_METRICS_ENERGY_CONSUMPTION_RADIO_H 00021 00022 #include "util/delegates/delegate.hpp" 00023 #include <util/pstl/vector_static.h> 00024 #include <util/pstl/pair.h> 00025 00026 //TODO: REMOVE!!!!!!! 00027 #include "sys/processor.h" 00028 #include "sys/event_scheduler.h" 00029 #include "sys/misc/random/random_variable.h" 00030 #include "sys/misc/random/random_variable_keeper.h" 00031 #include "sys/node.h" 00032 #include "sys/simulation/simulation_controller.h" 00033 #include "sys/simulation/simulation_environment.h" 00034 #include "sys/taggings/basic_tags.h" 00035 #include "sys/tag.h" 00036 00037 namespace wiselib { 00038 00039 template<typename OsModel_P, 00040 typename Radio_P = typename OsModel_P::Radio> 00041 class EnergyConsumptionRadioCallback 00042 { 00043 public: 00044 typedef OsModel_P OsModel; 00045 typedef typename OsModel::Os Os; 00046 typedef Radio_P Radio; 00047 00048 typedef EnergyConsumptionRadioCallback <OsModel, Radio> self_type; 00049 00050 typedef typename Radio::node_id_t node_id_t; 00051 typedef typename Radio::size_t size_t; 00052 typedef typename Radio::block_data_t block_data_t; 00053 typedef typename Radio::radio_delegate_t energy_consumption_delegate_t; 00054 // ----------------------------------------------------------------- 00055 EnergyConsumptionRadioCallback( Os *os, energy_consumption_delegate_t del ) 00056 : os_ ( os ), 00057 del_( del ) 00058 {} 00059 // ----------------------------------------------------------------- 00060 ~EnergyConsumptionRadioCallback() 00061 {} 00062 // ----------------------------------------------------------------- 00063 void receive( node_id_t id, size_t len, block_data_t* data ) 00064 { 00065 double e = os_->proc->owner().template read_simple_tag<double>( "energy" ); 00066 double rx = ((((15. + len) * 8.) / 250.) * 44.) / (3600. * 1000.); 00067 e += rx; 00068 os_->proc->owner_w().template write_simple_tag<double>( "energy", e ); 00069 00070 double consumed = os_->proc->owner().template read_simple_tag<double>( "consumed-rx" ); 00071 consumed += e; 00072 00073 bool app_active = os_->proc->owner().template read_simple_tag<bool>( "app_active" ); 00074 if ( app_active ) 00075 os_->proc->owner_w().template write_simple_tag<double>( "consumed-rx", consumed ); 00076 // std::cout << "consumed rx .... " << rx << "; all " << e << std::endl; 00077 00078 if ( del_ ) 00079 del_( id, len, data ); 00080 } 00081 // ----------------------------------------------------------------- 00082 bool is_empty() 00083 { return !del_; }; 00084 // ----------------------------------------------------------------- 00085 void clear() 00086 { del_ = energy_consumption_delegate_t(); }; 00087 // ----------------------------------------------------------------- 00088 energy_consumption_delegate_t delegate() 00089 { return del_; }; 00090 00091 private: 00092 Os *os_; 00093 energy_consumption_delegate_t del_; 00094 }; 00095 00096 00102 template<typename OsModel_P, 00103 typename Radio_P, 00104 typename Clock_P> 00105 class EneryConsumptionRadioModel { 00106 public: 00107 typedef OsModel_P OsModel; 00108 typedef Radio_P Radio; 00109 typedef Clock_P Clock; 00110 typedef EneryConsumptionRadioModel <OsModel, Radio, Clock> self_type; 00111 00112 typedef typename Radio::node_id_t node_id_t; 00113 typedef typename Radio::size_t size_t; 00114 typedef typename Radio::block_data_t block_data_t; 00115 typedef typename Radio::message_id_t message_id_t; 00116 00117 typedef typename Clock::time_t time_t; 00118 00119 typedef typename Radio::radio_delegate_t energy_consumption_delegate_t; 00120 typedef EnergyConsumptionRadioCallback<OsModel> RadioCallback; 00121 // -------------------------------------------------------------------- 00122 enum SpecialNodeIds { 00123 BROADCAST_ADDRESS = Radio::BROADCAST_ADDRESS, 00124 NULL_NODE_ID = Radio::NULL_NODE_ID 00125 }; 00126 // -------------------------------------------------------------------- 00127 enum Restrictions { 00128 MAX_MESSAGE_LENGTH = Radio::MAX_MESSAGE_LENGTH 00129 }; 00130 // -------------------------------------------------------------------- 00131 void 00132 send(node_id_t id, size_t len, block_data_t *data) 00133 { 00134 // TODO 00135 // double tx = ((((15. + len) * 8.) / 250.) * 44.) / (3600. * 1000.); 00136 // double e = energy( os ) + tx; 00137 // set_energy( os, e ); 00138 // double consumed = os->proc->owner().template read_simple_tag<double>( "consumed-tx" ); 00139 // consumed += e; 00140 // if ( app_active(os) ) 00141 // os->proc->owner_w().template write_simple_tag<double>( "consumed-tx", consumed ); 00142 // std::cout << "consumed tx .... " << tx << "; all " << e << std::endl; 00143 00144 radio().send( id, len, data ); 00145 } 00146 // -------------------------------------------------------------------- 00147 void init( Radio& radio, Clock& clock ) 00148 { 00149 radio_ = &radio; 00150 clock_ = &clock; 00151 } 00152 // -------------------------------------------------------------------- 00153 void destruct() 00154 {} 00155 // -------------------------------------------------------------------- 00156 void enable_radio() 00157 { 00158 // consume_period( os ); 00159 // set_activity( os, true ); 00160 00161 radio().enable_radio(); 00162 } 00163 // -------------------------------------------------------------------- 00164 void disable_radio() 00165 { 00166 // consume_period( os ); 00167 // set_activity( os, false ); 00168 00169 radio().disable_radio(); 00170 } 00171 // -------------------------------------------------------------------- 00172 node_id_t id() 00173 { 00174 return radio().id(); 00175 } 00176 // -------------------------------------------------------------------- 00177 template<class T, void (T::*TMethod)(node_id_t, size_t, block_data_t*)> 00178 int reg_recv_callback( T *obj_pnt ) 00179 { 00180 energy_consumption_delegate_t del = 00181 energy_consumption_delegate_t::template from_method<T, TMethod>( obj_pnt ); 00182 00183 RadioCallback *cb = new RadioCallback( del ); 00184 return radio().template reg_recv_callback<RadioCallback, &RadioCallback::receive>( cb ); 00185 } 00186 // -------------------------------------------------------------------- 00187 void unreg_recv_callback( int idx ) 00188 { 00189 radio().unreg_recv_callback( idx ); 00190 } 00191 00192 private: 00193 00194 // static void consume_period( Os *os ) 00195 // { 00196 // // TODO: Replace with local storage! 00197 // if ( data_available(os) ) 00198 // { 00199 // set_energy( os, 0.0 ); 00200 // set_last_changed( os, Clock::time(os) ); 00201 // set_activity( os, true ); 00202 // } 00203 // else 00204 // { 00205 // double consumed = 0.0; 00206 // if ( activity(os) ) 00207 // { 00208 // consumed = (Clock::time(os) - last_changed(os)) * 12.8 / (3600. * 1000.); 00209 // double tmp = os->proc->owner().template read_simple_tag<double>( "consumed-active" ); 00210 // tmp += consumed; 00211 // if ( app_active(os) ) 00212 // os->proc->owner_w().template write_simple_tag<double>( "consumed-active", tmp ); 00213 // } 00214 // else 00215 // { 00216 // consumed = (Clock::time(os) - last_changed(os)) * 0.025 / (3600. * 1000.); 00217 // double tmp = os->proc->owner().template read_simple_tag<double>( "consumed-idle" ); 00218 // tmp += consumed; 00219 // if ( app_active(os) ) 00220 // os->proc->owner_w().template write_simple_tag<double>( "consumed-idle", tmp ); 00221 // } 00222 // double e = energy( os ) + consumed; 00223 // // std::cout << "consumed t .... " << activity(os) << "; " << consumed << "; all " << e << std::endl; 00224 // 00225 // set_energy( os, e ); 00226 // set_last_changed( os, Clock::time(os) ); 00227 // } 00228 // } 00229 // // -------------------------------------------------------------------- 00230 // static bool data_available( Os *os ) 00231 // { 00232 // return os->proc->owner().find_tag( "energy" ) == 0 || 00233 // os->proc->owner().find_tag( "changed" ) == 0 || 00234 // os->proc->owner().find_tag( "activity" ) == 0; 00235 // } 00236 // // -------------------------------------------------------------------- 00237 // static void set_activity( Os *os, bool active ) 00238 // { 00239 // os->proc->owner_w().template write_simple_tag<bool>( "activity", active ); 00240 // } 00241 // // -------------------------------------------------------------------- 00242 // static void set_last_changed( Os *os, time_t time ) 00243 // { 00244 // os->proc->owner_w().template write_simple_tag<double>( "changed", time ); 00245 // } 00246 // // -------------------------------------------------------------------- 00247 // static void set_energy( Os *os, double e ) 00248 // { 00249 // os->proc->owner_w().template write_simple_tag<double>( "energy", e ); 00250 // } 00251 // // -------------------------------------------------------------------- 00252 // static bool activity( Os *os ) 00253 // { 00254 // return os->proc->owner().template read_simple_tag<bool>( "activity" ); 00255 // } 00256 // // -------------------------------------------------------------------- 00257 // static time_t last_changed( Os *os ) 00258 // { 00259 // return os->proc->owner().template read_simple_tag<double>( "changed" ); 00260 // } 00261 // // -------------------------------------------------------------------- 00262 // static double energy( Os *os ) 00263 // { 00264 // return os->proc->owner().template read_simple_tag<double>( "energy" ); 00265 // } 00266 // // -------------------------------------------------------------------- 00267 00268 // public: 00269 // static void set_app_active( Os *os, bool active ) 00270 // { 00271 // os->proc->owner_w().template write_simple_tag<bool>( "app_active", active ); 00272 // } 00273 // // -------------------------------------------------------------------- 00274 // static bool app_active( Os *os ) 00275 // { 00276 // return os->proc->owner().template read_simple_tag<bool>( "app_active" ); 00277 // } 00278 00279 private: 00280 Radio& radio() 00281 { return radio_; } 00282 00283 Clock& clock() 00284 { return clock_; } 00285 00286 Radio *radio_; 00287 Clock *clock_; 00288 00289 }; 00290 00291 } 00292 00293 #endif