00001 00030 #include <itpp/protocol/packet_channel.h> 00031 #include <itpp/base/random.h> 00032 #include <itpp/base/sort.h> 00033 #include <itpp/base/math/min_max.h> 00034 00035 00036 namespace itpp { 00037 00038 Packet_Channel::Packet_Channel() { 00039 parameters_ok = false; 00040 keep_running = false; 00041 } 00042 00043 Packet_Channel::Packet_Channel(const double Pr, const Ttype Delay, const double Block_rate, const int Max_slots) { 00044 set_parameters(Pr, Delay, Block_rate, Max_slots); 00045 } 00046 00047 00048 Packet_Channel::~Packet_Channel(){} 00049 00050 void Packet_Channel::set_parameters(const double Pr, const Ttype Delay, const double Block_rate, const int Max_slots) { 00051 it_assert(Delay >= 0,"Packet_Channel::set_parameters(): "); 00052 it_assert(Pr>=0.0 && Pr<=1.0,"Packet_Channel::set_parameters(): "); 00053 it_assert(Block_rate > 0,"Packet_Channel::set_parameters(): "); 00054 it_assert(Max_slots >= 0,"Packet_Channel::set_parameters(): "); 00055 delay = Delay; 00056 pr = Pr; 00057 block_time = 1.0/Block_rate; 00058 max_slots = Max_slots; 00059 input.forward(this, &Packet_Channel::handle_input); 00060 nof_inputs.forward(this, &Packet_Channel::handle_nof_inputs); 00061 start.forward(this, &Packet_Channel::handle_start); 00062 keep_running = false; 00063 explicit_errors = false; 00064 K = 0; 00065 k = 0; 00066 parameters_ok = true; 00067 } 00068 00069 void Packet_Channel::handle_input(Link_Packet* M) { 00070 it_assert(parameters_ok,"Packet_Channel::handle_input(): "); 00071 it_assert(M!=NULL,"Packet_Channel::handle_input(): "); 00072 if(explicit_errors){ 00073 if(k<L){ 00074 lose = lost(k)==K; 00075 if(lose) 00076 k++; 00077 } 00078 K++; 00079 } 00080 else 00081 lose = randu() < pr; 00082 if(lose){ 00083 delete M; 00084 } 00085 else 00086 output(M, delay); 00087 lose = false; 00088 } 00089 00090 void Packet_Channel::block_rate_loop() { 00091 it_assert(parameters_ok,"Packet_Channel::block_rate_loop(): "); 00092 get_nof_inputs(NULL); 00093 if(keep_running) 00094 Event_Queue::add(new Event<Packet_Channel>(this, &Packet_Channel::block_rate_loop, block_time)); 00095 } 00096 00097 void Packet_Channel::handle_start(const bool run) { 00098 it_assert(parameters_ok,"Packet_Channel::handle_start(): "); 00099 if(run&&!keep_running)// Channel is in 'stop' state. Start it and keep running. 00100 Event_Queue::add(new Event<Packet_Channel>(this, &Packet_Channel::block_rate_loop, block_time)); 00101 keep_running = run; 00102 } 00103 00104 void Packet_Channel::handle_nof_inputs(const int Nof_ready_messages) { 00105 it_assert(Nof_ready_messages>=0,"Packet_Channel::handle_nof_inputs(): "); 00106 int L = 0; 00107 if(max_slots>0) 00108 L = std::min(Nof_ready_messages, round_i(randu()*max_slots)); 00109 else 00110 L = std::min(Nof_ready_messages, 1); 00111 if(L>0) 00112 input_request(L); 00113 } 00114 00115 void Packet_Channel::set_errors(const ivec &Lost) { 00116 L = Lost.length(); 00117 if(L>0){ 00118 it_assert(min(Lost)>=0,"Packet_Channel::set_errors(): "); 00119 lost = Lost; 00120 sort(lost); 00121 explicit_errors = true; 00122 } 00123 } 00124 00125 00126 // ----------------------------- Ack_Channel -------------------------------- 00127 00128 00129 ACK_Channel::ACK_Channel() { 00130 parameters_ok = false; 00131 } 00132 00133 ACK_Channel::ACK_Channel(const double Pr, const Ttype Delay) { 00134 set_parameters(Pr, Delay); 00135 } 00136 00137 00138 ACK_Channel::~ACK_Channel(){} 00139 00140 void ACK_Channel::set_parameters(const double Pr, const Ttype Delay) { 00141 it_assert(Delay >= 0,"ACK_Channel::set_parameters(): "); 00142 it_assert(Pr>=0.0 && Pr<=1.0,"ACK_Channel::set_parameters(): "); 00143 delay = Delay; 00144 pr = Pr; 00145 input.forward(this, &ACK_Channel::handle_input); 00146 explicit_errors = false; 00147 K = 0; 00148 k = 0; 00149 parameters_ok = true; 00150 } 00151 00152 void ACK_Channel::handle_input(ACK* M) { 00153 it_assert(parameters_ok,"ACK_Channel::handle_input(): "); 00154 it_assert(M!=NULL,"ACK_Channel::handle_input(): "); 00155 if(explicit_errors){ 00156 if(k<L){ 00157 lose = lost(k)==K; 00158 if(lose) 00159 k++; 00160 } 00161 K++; 00162 } 00163 else 00164 lose = randu() < pr; 00165 if(lose) 00166 delete M; 00167 else 00168 output(M, delay); 00169 lose = false; 00170 } 00171 00172 void ACK_Channel::set_errors(const ivec& Lost) { 00173 L = Lost.length(); 00174 if(L>0){ 00175 it_assert(min(Lost)>=0,"ACK_Channel::set_errors(): "); 00176 lost = Lost; 00177 sort(lost); 00178 explicit_errors = true; 00179 } 00180 } 00181 00182 } // namespace itpp
Generated on Sun Dec 9 17:30:27 2007 for IT++ by Doxygen 1.5.4