DESERT 3.5.1
Loading...
Searching...
No Matches
uw-smart-ofdm.cpp
Go to the documentation of this file.
1//
2// Copyright (c) 2017 Regents of the SIGNET lab, University of Padova.
3// All rights reserved.
4//
5// Redistribution and use in source and binary forms, with or without
6// modification, are permitted provided that the following conditions
7// are met:
8// 1. Redistributions of source code must retain the above copyright
9// notice, this list of conditions and the following disclaimer.
10// 2. Redistributions in binary form must reproduce the above copyright
11// notice, this list of conditions and the following disclaimer in the
12// documentation and/or other materials provided with the distribution.
13// 3. Neither the name of the University of Padova (SIGNET lab) nor the
14// names of its contributors may be used to endorse or promote products
15// derived from this software without specific prior written permission.
16//
17// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
19// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
20// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
21// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
22// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
23// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
24// OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
25// WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
26// OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
27// ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28
38#include "uw-smart-ofdm.h"
39#include <mac.h>
40#include <cmath>
41#include <climits>
42#include <iomanip>
43#include <rng.h>
44#include "uwphy-clmsg.h"
45
46enum
47{
48 NOT_SET = -1,
50};
51
55static class UWSMARTOFDMModuleClass : public TclClass
56{
57public:
62 : TclClass("Module/UW/SMART_OFDM")
63 {
64 }
65
66 TclObject *
67 create(int, const char *const *)
68 {
69 return (new UWSmartOFDM());
70 }
72
74{
76 if (module->curr_state == UWSMARTOFDM_STATE_WAIT_ACK)
77 {
78
79 if (module->uwsmartofdm_debug)
80 cout << NOW << " UWSmartOFDM (" << module->addr
81 << ") ACK_timer expire() current state = "
82 << module->status_info[module->curr_state]
83 << "; ACK not received, next state = "
84 << module->status_info[UWSMARTOFDM_STATE_BACKOFF] << endl;
85
86 module->refreshReason(UWSMARTOFDM_REASON_ACK_TIMEOUT);
87 module->stateBackoff();
88 }
89 else
90 {
91 if (module->uwsmartofdm_debug)
92 cout << NOW << " UWSmartOFDM (" << module->addr
93 << ")::AckTimer::expired() " << endl;
94 }
95}
96
97void UWSmartOFDM::BackOffTimer::expire(Event *e)
98{
99 timer_status = UWSMARTOFDM_EXPIRED;
100 if (module->curr_state == UWSMARTOFDM_STATE_BACKOFF)
101 {
102
103 if (module->uwsmartofdm_debug)
104 cout << NOW << " UWSmartOFDM (" << module->addr
105 << ") timer expire() current state = "
106 << module->status_info[module->curr_state]
107 << "; backoff expired, next state = "
108 << module->status_info[UWSMARTOFDM_STATE_IDLE] << endl;
109
111 module->exitBackoff();
112 if (module->current_rcvs == 0)
113 module->stateIdle();
114 else
116 }
117 else
118 {
119 if (module->uwsmartofdm_debug)
120 cout << NOW << " UWSmartOFDM (" << module->addr
121 << ")::BackOffTimer::expired() " << endl;
122 }
123}
124
125// Packets can't be sent while waiting for CTS
126// The only thing that can happen is that something is being received
127// When this expires the state always has to be UWSMARTOFDM_STATE_CTRL_BACKOFF
129{
130 if (module->uwsmartofdm_debug)
131 cout << NOW << " UWSmartOFDM (" << module->addr
132 << ") CTS TIMER EXPIRED" << endl;
134 module->RTSvalid = true;
135 module->refreshReason(UWSMARTOFDM_REASON_CTS_BACKOFF_TIMEOUT);
136 if (module->current_rcvs == 0)
137 {
138
139 if (module->uwsmartofdm_debug)
140 cout << NOW << " UWSmartOFDM (" << module->addr
141 << ") CTStimer expire() current state = "
142 << module->status_info[module->curr_state]
143 << "; backoff expired, next state = "
144 << module->status_info[UWSMARTOFDM_STATE_TX_RTS] << endl;
145
146 module->exitCTSBackoff();
147 module->Mac2PhySetTxBusy(1);
148 module->stateSendRTS();
149 }
150 else
151 {
152 module->refreshState(UWSMARTOFDM_STATE_IDLE);
153 if (module->uwsmartofdm_debug)
154 cout << NOW << " UWSmartOFDM (" << module->addr
155 << ") CTStimer expire() current state = "
156 << module->status_info[module->curr_state]
157 << "; backoff expired, next state = "
158 << module->status_info[UWSMARTOFDM_STATE_IDLE] << endl;
159 }
160}
161
162// While RTSvalid == false I can't be sending DATA
163// can only send CTS but in that case state is not IDLE
164void UWSmartOFDM::RTSTimer::expire(Event *e)
165{
166 module->RTSvalid = true;
167 timer_status = UWSMARTOFDM_EXPIRED;
168 if (module->curr_state == UWSMARTOFDM_STATE_IDLE && module->current_rcvs == 0)
169 {
170 if (module->uwsmartofdm_debug)
171 cout << NOW << " UWSmartOFDM (" << module->addr
172 << ") RTStimer expire(), stateIDLE, sending RTS again " << std::endl;
173 module->Mac2PhySetTxBusy(1);
174 module->stateSendRTS();
175 }
176 else
177 {
178 if (module->uwsmartofdm_debug)
179 cout << NOW << " UWSmartOFDM (" << module->addr
180 << ") RTStimer expire(), BUT doing other stuff, keep going " << std::endl;
181 }
182}
183
185{
186 // cout << NOW << " UWSmartOFDM (" << module->addr << ") Assignment TIMER EXPIRED" << endl;
188
189 module->clearOccTable();
190 if (module->curr_state == UWSMARTOFDM_STATE_IDLE && module->current_rcvs == 0)
191 {
192 module->stateIdle();
193 }
194}
195
197{
199
200 module->resetAssignment();
201}
202
203// While DATAtimer is active, the node can't send packets because it's waiting to receive them
205{
207 module->refreshReason(UWSMARTOFDM_REASON_DATAT_EXPIRED);
208 if (module->uwsmartofdm_debug)
209 cout << NOW << " UWSmartOFDM (" << module->addr
210 << ") DATATimer expire() " << std::endl;
211
212 if (module->current_rcvs == 0)
213 module->stateIdle();
214 else
215 module->refreshState(UWSMARTOFDM_STATE_IDLE);
216}
217
218const double UWSmartOFDM::prop_speed = 1500.0;
219bool UWSmartOFDM::initialized = false;
220
221map<UWSmartOFDM::UWSMARTOFDM_STATUS, string> UWSmartOFDM::status_info;
222map<UWSmartOFDM::UWSMARTOFDM_REASON_STATUS, string> UWSmartOFDM::reason_info;
223map<UWSmartOFDM::UWSMARTOFDM_PKT_TYPE, string> UWSmartOFDM::pkt_type_info;
224
226 : ack_timer(this), backoff_timer(this), CTS_timer(this),
228 RTS_timer(this), DATA_timer(this), txsn(1), last_sent_data_id(-1),
233 start_tx_time(0), recv_data_id(-1), srtt(0), sumrtt(0), sumrtt2(0), rttsamples(0),
236 batch_sending(false), RTSvalid(true), max_rts_tries(0), nextFreeTime(0),
237 ackToSend(false), waitPkt(0), nextRTSts(0), nextRTS(0), fullBand(false)
238{
239 bind("HDR_size_", (int *)&HDR_size);
240 bind("ACK_size_", (int *)&ACK_size);
241 bind("RTS_size_", (int *)&RTS_size);
242 bind("CTS_size_", (int *)&CTS_size);
243 bind("DATA_size_", (int *)&DATA_size);
244 bind("bitrateCar_", (double *)&bitrateCar);
245 bind("max_tx_tries_", (int *)&max_tx_tries);
246 bind("max_rts_tries_", (int *)&max_rts_tries);
247 bind("wait_constant_", (double *)&wait_constant);
248 bind("uwsmartofdm_debug_", (int *)&uwsmartofdm_debug); // debug mode
249 bind("max_payload_", (int *)&max_payload);
250 bind("ACK_timeout_", (double *)&ACK_timeout);
251 bind("alpha_", (double *)&alpha_);
252 bind("buffer_pkts_", (int *)&buffer_pkts);
253 bind("backoff_tuner_", (double *)&backoff_tuner);
254 bind("max_backoff_counter_", (int *)&max_backoff_counter);
255 bind("nodenum_", (int *)&nodeNum);
256 bind("timeslots_", (int *)&timeslots);
257 bind("timeslot_length_", (double *)&timeslot_length);
258 bind("max_car_reserved_", (int *)&max_car_reserved);
259 bind("req_tslots_", (int *)&req_tslots);
260 bind("MAC_addr_", (int *)&addr);
261 bind("print_transitions_", (int *)&print_transitions);
262 bind("max_burst_size_", (int *)&max_burst_size);
263 bind("fullBand_", (int *)&fullBand);
264
265 if (max_tx_tries <= 0)
266 max_tx_tries = INT_MAX;
267 if (buffer_pkts > 0)
268 has_buffer_queue = true;
269
270 msgDisp.initDisplayer(addr, "UWSmartOFDM", uwsmartofdm_debug);
271}
272
276
277// TCL command interpreter
278
279int UWSmartOFDM::command(int argc, const char *const *argv)
280{
281 Tcl &tcl = Tcl::instance();
282 if (argc == 2)
283 {
284 if (strcasecmp(argv[1], "setAckMode") == 0)
285 {
287 return TCL_OK;
288 }
289 else if (strcasecmp(argv[1], "setNoAckMode") == 0)
290 {
292 return TCL_OK;
293 }
294 else if (strcasecmp(argv[1], "initialize") == 0)
295 {
296 if (initialized == false)
297 initInfo();
299 fout.open("/tmp/SMARTOFDMstateTransitions.txt", ios_base::app);
300 return TCL_OK;
301 }
302 else if (strcasecmp(argv[1], "printTransitions") == 0)
303 {
304 print_transitions = true;
305 return TCL_OK;
306 } // stats functions
307 else if (strcasecmp(argv[1], "getQueueSize") == 0)
308 {
309 tcl.resultf("%d", mapPacket.size());
310 return TCL_OK;
311 }
312 else if (strcasecmp(argv[1], "getUpLayersDataRx") == 0)
313 {
314 tcl.resultf("%d", getUpLayersDataPktsRx());
315 return TCL_OK;
316 }
317 else if (strcasecmp(argv[1], "getAckPktsTx") == 0)
318 {
319 tcl.resultf("%d", getAckPktsTx());
320 return TCL_OK;
321 }
322 else if (strcasecmp(argv[1], "getHighPrioPktsSent") == 0)
323 {
324 tcl.resultf("%d", getHighPrioPktsSent());
325 return TCL_OK;
326 }
327 else if (strcasecmp(argv[1], "getHighPrioPktsRecv") == 0)
328 {
329 tcl.resultf("%d", getHighPrioPktsRecv());
330 return TCL_OK;
331 }
332 }
333 else if (argc == 3)
334 {
335 if (strcasecmp(argv[1], "setMacAddr") == 0)
336 {
337 addr = atoi(argv[2]);
338 if (debug_)
339 cout << "OFDM Aloha MAC address of current node is " << addr << endl;
340 return TCL_OK;
341 }
342 if (strcasecmp(argv[1], "addInvalidCarriers") == 0)
343 {
344 addInvalidCarriers(atoi(argv[2]));
345 if (debug_)
346 cout << "Carrier " << atoi(argv[2]) << " not usable " << endl;
347 return TCL_OK;
348 }
349 }
350 else if (argc == 6)
351 {
352 if (strcasecmp(argv[1], "init_macofdm_node") == 0)
353 {
354 init_macofdm_node(atoi(argv[2]), atof(argv[3]), atoi(argv[4]), argv[5]);
355 return TCL_OK;
356 }
357 }
358 return MMac::command(argc, argv);
359}
360
362{
363
364 initialized = true;
365
366 if ((print_transitions) && (system(NULL)))
367 {
368 system("rm -f /tmp/SMARTOFDMstateTransitions.txt");
369 system("touch /tmp/SMARTOFDMstateTransitions.txt");
370 }
371
372 status_info[UWSMARTOFDM_STATE_IDLE] = "Idle state";
373 status_info[UWSMARTOFDM_STATE_TX_DATA] = "Transmit DATA state";
374 status_info[UWSMARTOFDM_STATE_TX_ACK] = "Transmit ACK state";
375 status_info[UWSMARTOFDM_STATE_WAIT_ACK] = "Wait for ACK state";
376 status_info[UWSMARTOFDM_STATE_DATA_RX] = "DATA received state";
377 status_info[UWSMARTOFDM_STATE_ACK_RX] = "ACK received state";
378 status_info[UWSMARTOFDM_STATE_RX_IDLE] = "Start rx Idle state";
379 status_info[UWSMARTOFDM_STATE_RX_WAIT_ACK] = "Start rx Wait ACK state";
380 status_info[UWSMARTOFDM_STATE_CHK_ACK_TIMEOUT] = "Check Wait ACK timeout state";
381 status_info[UWSMARTOFDM_STATE_WRONG_PKT_RX] = "Wrong Pkt Rx state";
382 status_info[UWSMARTOFDM_STATE_BACKOFF] = "Backoff state";
383 status_info[UWSMARTOFDM_STATE_RX_BACKOFF] = "Start rx Backoff state";
384 status_info[UWSMARTOFDM_STATE_CHK_BACKOFF_TIMEOUT] = "Check Backoff timeout state";
385 status_info[UWSMARTOFDM_STATE_TX_RTS] = "Transmit RTS state";
386 status_info[UWSMARTOFDM_STATE_RX_RTS] = "Receive RTS state";
387 status_info[UWSMARTOFDM_STATE_WAIT_CTS] = "Wait for CTS state";
388 status_info[UWSMARTOFDM_STATE_CTRL_BACKOFF] = "Start CTRL backoff state";
389 status_info[UWSMARTOFDM_STATE_TX_CTS] = "Transmit CTS state";
390 status_info[UWSMARTOFDM_STATE_RX_CTS] = "Receive CTS state";
391 status_info[UWSMARTOFDM_STATE_RX_ACTIVE] = "Active Reception state";
392 status_info[UWSMARTOFDM_STATE_TX_ACTIVE] = "Active Transmission state";
393 status_info[UWSMARTOFDM_STATE_WAIT_DATA] = "Wait for DATA state";
394
395 reason_info[UWSMARTOFDM_REASON_DATA_PENDING] = "DATA pending from upper layers";
396 reason_info[UWSMARTOFDM_REASON_DATA_RX] = "DATA received";
397 reason_info[UWSMARTOFDM_REASON_DATA_TX] = "DATA transmitted";
398 reason_info[UWSMARTOFDM_REASON_ACK_TX] = "ACK tranmsitted";
399 reason_info[UWSMARTOFDM_REASON_ACK_RX] = "ACK received";
400 reason_info[UWSMARTOFDM_REASON_DATA_NOCAR] = "DATA to send & carriers not assigned";
401 reason_info[UWSMARTOFDM_REASON_DATA_CARASSIGNED] = "DATA to send & carriers already assigned";
402 reason_info[UWSMARTOFDM_REASON_RTS_RX] = "RTS received";
403 reason_info[UWSMARTOFDM_REASON_CTS_RX] = "CTS received";
405 reason_info[UWSMARTOFDM_REASON_DATA_EMPTY] = "DATA queue empty";
407 "DATA dropped due to max tx rounds";
409 reason_info[UWSMARTOFDM_REASON_PKT_NOT_FOR_ME] = "Received an erroneous pkt";
410 reason_info[UWSMARTOFDM_REASON_WAIT_ACK_PENDING] = "Wait for ACK timer pending";
411 reason_info[UWSMARTOFDM_REASON_PKT_ERROR] = "Pkt corrupted at PHY layer";
413 reason_info[UWSMARTOFDM_REASON_BACKOFF_PENDING] = "Backoff timer pending";
414 reason_info[UWSMARTOFDM_REASON_WAIT_CTS_PENDING] = "CTS Backoff timer pending";
415 reason_info[UWSMARTOFDM_REASON_CTS_TX] = "CTS transmitted";
416 reason_info[UWSMARTOFDM_REASON_RTS_TX] = "RTS transmitted";
418 reason_info[UWSMARTOFDM_REASON_PHY_LAYER_RECEIVING] = "Phy Layer receiving something";
419 reason_info[UWSMARTOFDM_REASON_PHY_LAYER_SENDING] = "Phy Layer sending something";
420 reason_info[UWSMARTOFDM_REASON_MAX_RTS_TRIES] = "Max RTS tries reached";
421 reason_info[UWSMARTOFDM_REASON_WAIT_DATA] = "CTS Sent, waiting for DATA to arrive";
422 reason_info[UWSMARTOFDM_REASON_DATAT_EXPIRED] = "DATA Timer Expired";
423 reason_info[UWSMARTOFDM_REASON_PREVIOUS_RTS] = "Previously received and RTS";
424
427 pkt_type_info[UWSMARTOFDM_DATAMAX_PKT] = "MAX payload DATA pkt";
430}
431
432// Initialize subCarriers parameters inside a node, default all carriers are used
433void UWSmartOFDM::init_macofdm_node(int subCarNum, double carSize, int ctrl_subCar, std::string modulation)
434{
435
436 mac_ncarriers = subCarNum;
437 ctrl_car = ctrl_subCar;
439
440 mac_carrierSize = carSize;
441
443
444 // Occupancy_table initialization with all 0s (free)
445 for (int i = 0; i < data_car; i++)
446 {
447
448 std::vector<int> temp;
449 for (int j = 0; j < timeslots; j++)
450 temp.push_back(0);
451
452 otabmtx.lock();
453 occupancy_table.push_back(temp);
454 otabmtx.unlock();
455 }
456
457 for (int i = 0; i < mac_ncarriers; i++)
458 {
459 std::vector<double> temp;
460 temp.push_back(0);
461 interf_table.push_back(temp);
462 }
463
464 // This is kept for carriers not to be used at all
465 for (int i = 0; i < nouse_carriers.size(); i++)
466 {
467 for (int j = 0; j < timeslots; j++)
469 }
470 // mac_carVec initialization (since it's a vector!)
471 for (int i = 0; i < data_car; i++)
472 {
473 mac_carVec.push_back(0);
474 }
475 // mac_carMod initialization (since it's a vector!)
476 for (int i = 0; i < mac_ncarriers; i++)
477 {
478 mac_carMod.push_back("BPSK");
479 }
480 return;
481}
482
483void UWSmartOFDM::updateRTT(double curr_rtt)
484{
485 srtt = alpha_ * srtt + (1 - alpha_) * curr_rtt;
486 sumrtt += curr_rtt;
487 sumrtt2 += curr_rtt * curr_rtt;
488 rttsamples++;
490}
491
493{
494 updateRTT(rtt);
495 // double curr_rtt = getRTT();
496
497 // if (curr_rtt > 0) ACK_timeout = min(ACK_timeout, getRTT() );
498
500 cout << NOW << " UWSmartOFDM (" << addr
501 << ")::updateAckTimeout() curr ACK_timeout = " << ACK_timeout
502 << endl;
503 // waitForUser();
504}
505
510
515
516double
518{
519 incrTotalBackoffTimes();
520 double random = RNG::defaultrng()->uniform_double();
521
526
527 double backoff_duration =
528 backoff_tuner * random * 2.0 * ACK_timeout * pow(2.0, counter);
529
530 backoffSumDuration(backoff_duration);
531
533 {
534 cout << NOW << " UWSmartOFDM (" << addr
535 << ")::getBackoffTime() backoff time = " << backoff_duration
536 << " s" << endl;
537 }
538 return backoff_duration;
539}
540
541double
543{
544 double duration;
545 Packet *temp_data_pkt;
546 map<pktSeqNum, Packet *>::iterator it_p;
547
548 if (type == UWSMARTOFDM_DATA_PKT)
549 {
550 if (!mapPacket.empty())
551 {
552 it_p = mapPacket.begin();
553 temp_data_pkt = ((*it_p).second)->copy();
554 // temp_data_pkt = (Q.front())->copy();
555 hdr_cmn *ch = HDR_CMN(temp_data_pkt);
556 ch->size() = HDR_size + ch->size();
557 }
558 else
559 {
560 temp_data_pkt = Packet::alloc();
561 hdr_cmn *ch = HDR_CMN(temp_data_pkt);
562 ch->size() = HDR_size + max_payload;
563 }
564 }
565 else if (type == UWSMARTOFDM_ACK_PKT)
566 {
567 temp_data_pkt = Packet::alloc();
568 hdr_cmn *ch = HDR_CMN(temp_data_pkt);
569 ch->size() = ACK_size;
570 }
571 duration = Mac2PhyTxDuration(temp_data_pkt);
572 Packet::free(temp_data_pkt);
573 return (duration);
574}
575
577{
578 msgDisp.printStatus("", "recvFromUpperLayers", NOW, addr);
579 if (((has_buffer_queue == true) && (mapPacket.size() < buffer_pkts)) ||
580 (has_buffer_queue == false))
581 {
582 hdr_cmn *ch = hdr_cmn::access(p);
584 std::cout << NOW << " UWSmartOFDM (" << addr << ")::recvFromUpperLayers received packet seq_num = " << ch->uid() << std::endl;
586 putPktInQueue(p);
588 waitStartTime();
589
591 { // Basically not doing anything
592
594 hdr_mac *mach = HDR_MAC(p);
595 current_macDA = mach->macDA();
596 if (!car_assigned && RTSvalid)
597 {
598 msgDisp.printStatus("car_assigned = FALSE sending RTS", "recvFromUpperLayers", NOW, addr);
600 stateSendRTS();
601 }
602 else if (car_assigned)
603 {
604 msgDisp.printStatus("New data but car_assigned = TRUE", "recvFromUpperLayers", NOW, addr);
605 stateTxData();
606 }
607 else
608 {
609 msgDisp.printStatus("New data but RTS_valid = FALSE and car_assigned = FALSE", "recvFromUpperLayers", NOW, addr);
610 }
611 }
612 else
613 {
614 string st = "Not proceeding with RTS because in STATE: " + status_info[curr_state] + "or current_rcvs = " + std::to_string(current_rcvs);
615 msgDisp.printStatus(st, "recvFromUpperLayers", NOW, addr);
616 }
617 }
618 else
619 {
620 incrDiscardedPktsTx();
621 msgDisp.printStatus("Dropping packet", "recvFromUpperLayers", NOW, addr);
623 }
624}
625
626void UWSmartOFDM::initPkt(Packet *p, UWSMARTOFDM_PKT_TYPE type, int dest_addr)
627{
628 hdr_cmn *ch = hdr_cmn::access(p);
629 hdr_mac *mach = HDR_MAC(p);
630 hdr_MPhy *ph = HDR_MPHY(p);
631 hdr_OFDM *ofdmph = HDR_OFDM(p);
632 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(p);
633
635 {
636 std::cout << NOW << " UWSmartOFDM (" << addr << ")::initPkt() for a " << pkt_type_info[type] << " packet " << p << " seq_num " << ch->uid() << " size " << ch->size() << std::endl;
637 }
638 for (int i = 0; i < mac_carMod.size(); i++)
639 ofdmph->carMod[i] = mac_carMod[i];
640 ofdmph->carrierNum = mac_ncarriers;
642 ofdmph->nativeOFDM = true;
643
644 int curr_size = ch->size();
645
646 switch (type)
647 {
648
650 {
651 ch->size() = curr_size + HDR_size;
652 mach->ftype() = MF_DATA;
653 // std::cout << "DATA PKT, MAC DEST " << mach->macDA() << std::endl;
654 }
655 break;
656
657 case (UWSMARTOFDM_ACK_PKT):
658 {
659 ch->ptype() = PT_MMAC_ACK;
660 ch->size() = ACK_size;
661 ch->uid() = recv_data_id;
662 mach->ftype() = MF_ACK;
663 mach->macSA() = addr;
664 mach->macDA() = dest_addr;
665 }
666 break;
667
668 case (UWSMARTOFDM_RTS_PKT):
669 {
670 ch->ptype() = PT_MMAC_RTS;
671 ch->size() = RTS_size;
672 ch->uid() = recv_data_id;
673 mach->ftype() = MF_RTS;
674 mach->macSA() = addr;
675 mach->macDA() = dest_addr;
676 if (mapPacket.size() > max_burst_size)
678 else
679 ofdmmac->bytesToSend = DATA_size * mapPacket.size();
680 }
681 break;
682
683 case (UWSMARTOFDM_CTS_PKT):
684 {
685 ch->ptype() = PT_MMAC_CTS;
686 ch->size() = CTS_size;
687 ch->uid() = recv_data_id;
688 mach->ftype() = MF_CTS;
689 mach->macSA() = addr;
690 mach->macDA() = dest_addr;
691 }
692 break;
693 }
694 if (type != UWSMARTOFDM_DATA_PKT)
695 {
696 if (fullBand == false)
697 {
698 for (std::size_t i = 0; i < ctrl_car; ++i)
699 ofdmph->carriers[i] = 1;
700
701 for (std::size_t i = ctrl_car; i < mac_ncarriers; ++i)
702 ofdmph->carriers[i] = 0;
703 }
704 else
705 {
706 for (std::size_t i = 0; i < mac_ncarriers; ++i)
707 ofdmph->carriers[i] = 1;
708 }
709
710 for (std::size_t i = 0; i < mac_ncarriers; ++i)
711 ofdmph->carMod[i] = "BPSK";
712 }
713}
714
716{
717 hdr_cmn *ch = hdr_cmn::access(p);
718 hdr_mac *mach = HDR_MAC(p);
719
721 cout << NOW << " UWSmartOFDM (" << addr
722 << ")::Mac2PhyStartTx() _DBG_ start tx packet type " << ch->ptype()
723 << ", seq num = " << ch->uid()
724 << ", source addr = " << mach->macSA()
725 << ", dest addr = " << mach->macDA()
726 << ", current_rcvs = " << current_rcvs << std::endl;
727
728 MMac::Mac2PhyStartTx(p);
729
730 msgDisp.printStatus("Sent down packet, current_rcvs = " + std::to_string(current_rcvs), "Mac2PhyStartTx", NOW, addr);
731}
732
733void UWSmartOFDM::Phy2MacEndTx(const Packet *p)
734{
735 msgDisp.printStatus("End tx Packet", "Mac2PhyEndTx", NOW, addr);
736
738
739 switch (curr_state)
740 {
741
743 {
746 {
747
749 cout << NOW << " UWSmartOFDM (" << addr
750 << ")::Phy2MacEndTx() DATA sent,from "
751 << status_info[curr_state] << " to "
753
754 stateWaitAck();
755 }
756 else
757 {
758
760 cout << NOW << " UWSmartOFDM (" << addr
761 << ")::Phy2MacEndTx() DATA sent, from "
762 << status_info[curr_state] << " to "
764
765 stateIdle();
766 }
767 }
768 break;
769
771 {
773
775 cout << NOW << " UWSmartOFDM (" << addr
776 << ")::Phy2MacEndTx() ack sent, from "
777 << status_info[curr_state] << " to "
779 // stateIdle();
780 stateBackoff(0.0001); // this is for the scheduler precision
781 }
782 break;
785 {
787
789 cout << NOW << " UWSmartOFDM (" << addr
790 << ")::Phy2MacEndTx() RTS sent, from "
791 << status_info[curr_state] << " to "
794 }
795 break;
796
798 {
800
802 cout << NOW << " UWSmartOFDM (" << addr
803 << ")::Phy2MacEndTx() CTS sent, from "
804 << status_info[curr_state] << " to "
806 stateWaitData(0.3);
807 // stateIdle();
808 }
809 break;
811
812 default:
813 {
814 cout << NOW << " UWSmartOFDM (" << addr
815 << ")::Phy2MacEndTx() logical error, current state = "
816 << status_info[curr_state] << " prev state " << status_info[prev_state] << endl;
817 stateIdle();
818 // exit(1);
819 }
820 break;
821 }
822}
823
824void UWSmartOFDM::Phy2MacStartRx(const Packet *p)
825{
826 current_rcvs++;
828 cout << NOW << " UWSmartOFDM (" << addr << ")::Phy2MacStartRx() rx Packet. current_rcvs = " << current_rcvs << endl;
829}
830
832{
833 hdr_cmn *ch = HDR_CMN(p);
834 packet_t rx_pkt_type = ch->ptype();
835 hdr_mac *mach = HDR_MAC(p);
836 MacFrameType frame_type = mach->ftype();
837 hdr_MPhy *ph = HDR_MPHY(p);
838 hdr_OFDM *ofdmph = HDR_OFDM(p);
839
840 int source_mac = mach->macSA();
841 int dest_mac = mach->macDA();
842
843 double gen_time = ph->txtime;
844 double received_time = ph->rxtime;
845 double diff_time = received_time - gen_time;
846
847 double distance = diff_time * prop_speed;
848 current_rcvs--;
850 cout << NOW << " UWSmartOFDM (" << addr << ")::Phy2MacEndRx() _DBG_ "
852 << ", received a pkt type = " << ch->ptype()
853 << ", seq num = " << ch->uid()
854 << ", src addr = " << mach->macSA()
855 << " dest addr = " << mach->macDA()
856 << ", estimated distance between nodes = " << distance << " m. "
857 << "current_rcvs " << current_rcvs << endl;
858
859 if (ch->error())
860 { // this tells if there were errors at the phy layer
861 msgDisp.printStatus("dropping corrupted pkt", "Phy2MacEndRx()", NOW, addr);
862 incrErrorPktsRx();
863
866 if (current_rcvs == 0 && curr_state == UWSMARTOFDM_STATE_IDLE) // curr_state != UWSMARTOFDM_STATE_WAIT_DATA && curr_state != UWSMARTOFDM_STATE_CTRL_BACKOFF)
867 stateIdle();
868 // TODO: send ack if expected
869 }
870 else
871 { // no errors in the packet
872 if (dest_mac == addr || dest_mac == MAC_BROADCAST)
873 {
874 // Organized by Packet Types, pkt is for me
875 if (frame_type == MF_ACK) //(rx_pkt_type == PT_MMAC_ACK)
876 {
878 stateRxAck(p);
879 }
880 else if (frame_type == MF_CTS) //(rx_pkt_type == PT_MMAC_CTS)
881 {
882 // When receiving a CTS always go to set carriers and OTable
883 // If free will proceed with sending data
885 {
887 msgDisp.printStatus("going to stateRxCTS", "Phy2MacEndRx", NOW, addr);
888 stateRxCTS(p);
889 }
890 else
891 {
892 msgDisp.printStatus("Updating OTable but keep doing the other stuff, curr_state " + status_info[curr_state], "Phy2MacEndRx", NOW, addr);
893 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(p);
894 int slots = ofdmmac->timeReserved / timeslot_length;
895 updateOccupancy(ofdmmac->usage_carriers, slots + 1);
896 double newNextFreeT = NOW + ofdmmac->timeReserved;
897 if (newNextFreeT > nextFreeTime)
898 nextFreeTime = newNextFreeT;
899 }
900 }
901 else if (frame_type == MF_RTS) //(rx_pkt_type == PT_MMAC_RTS)
902 {
903 nextRTS = p->copy();
904 nextRTSts = NOW;
905 if (current_rcvs == 0 && ackToSend)
906 {
907
909 stateTxAck(HDR_MAC(pkt_to_ack)->macSA());
910 }
912 {
914 msgDisp.printStatus("going to stateRxRTS", "Phy2MacEndRx", NOW, addr);
915 stateRxRTS(p);
916 }
917 else
918 {
919 msgDisp.printStatus("RTS received but curr_state " + status_info[curr_state], "Phy2MacEndRx", NOW, addr);
921 }
922 }
923 else
924 {
925 // In case an unrecognized data packet arrives
926 if (frame_type != MF_RTS && frame_type != MF_CTS && frame_type != MF_ACK && frame_type != MF_DATA)
927 {
928 cerr << NOW << " UWSmartOFDM (" << addr << ")::Phy2MacEndRx Unrecognized packet addressed to me" << std::endl;
932 {
933 msgDisp.printStatus("Going Back To IDLE STATE", "Phy2MacEndRx", NOW, addr);
934 if (ackToSend)
935 {
937 stateTxAck(HDR_MAC(pkt_to_ack)->macSA());
938 }
939 else
940 stateIdle();
941 }
942 }
943 // Data Packet: In this case There are no follow up operations so I receive the packet in any case
944 // RxData doesn't disrupt the FSM cycle
946 {
948 msgDisp.printStatus("going to stateRxData", "Phy2MacEndRx", NOW, addr);
949 stateRxData(p);
950 }
951 else
952 {
953 msgDisp.printStatus("DATA received but curr_state " + status_info[curr_state], "Phy2MacEndRx", NOW, addr);
955 }
956 }
957 }
958 else
959 {
961 if (frame_type == MF_CTS) //(rx_pkt_type == PT_MMAC_CTS)
962 {
963 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(p);
964 msgDisp.printStatus("PKT NOT FOR ME 555x, UPDATING TABLE drop", "Phy2MacEndRx", NOW, addr);
965
966 int slots = ofdmmac->timeReserved / timeslot_length;
967 updateOccupancy(ofdmmac->usage_carriers, slots + 1);
968 double newNextFreeT = NOW + ofdmmac->timeReserved;
969 if (newNextFreeT > nextFreeTime)
970 nextFreeTime = newNextFreeT;
971 msgDisp.printStatus("nextFreeTime=" + std::to_string(nextFreeTime), "Phy2MacEndRx", NOW, addr);
973
975 {
976 msgDisp.printStatus("Going Back To IDLE STATE", "Phy2MacEndRx", NOW, addr);
977 if (ackToSend)
978 {
980 stateTxAck(HDR_MAC(pkt_to_ack)->macSA());
981 }
982 else
983 stateIdle();
984 }
985 else
986 {
987 msgDisp.printStatus("CTS received, not for me. Curr_state = " + status_info[curr_state], "Phy2MacEndRx", NOW, addr);
988 }
989 }
990 else
991 {
992 // Packet::free(p);
993 msgDisp.printStatus("PKT NOT FOR ME 222x drop", "Phy2MacEndRx", NOW, addr);
994
995 if (frame_type != MF_RTS && frame_type != MF_CTS && frame_type != MF_ACK && frame_type != MF_DATA)
996 {
997 msgDisp.printStatus("Unrecognized Packet Received", "Phy2MacEndRx", NOW, addr);
999 }
1002 {
1003 msgDisp.printStatus("Going Back To IDLE STATE 222x. Curr_state = " + status_info[curr_state], "Phy2MacEndRx", NOW, addr);
1004 if (ackToSend)
1005 {
1007 stateTxAck(HDR_MAC(pkt_to_ack)->macSA());
1008 }
1009 else
1010 {
1011 if (frame_type == MF_RTS) //(rx_pkt_type == PT_MMAC_RTS)
1012 stateBackoff(0.08);
1013 else
1014 stateIdle();
1015 }
1016 }
1017 }
1018 }
1019 }
1020}
1021
1023{
1024 Packet *data_pkt = curr_data_pkt->copy();
1025
1026 curr_rts_tries = 0;
1027
1029 {
1031 }
1032
1033 incrDataPktsTx();
1035 Mac2PhyStartTx(data_pkt);
1036}
1037
1038void UWSmartOFDM::txAck(int dest_addr)
1039{
1040 Packet *ack_pkt = Packet::alloc();
1041 initPkt(ack_pkt, UWSMARTOFDM_ACK_PKT, dest_addr);
1042
1043 incrAckPktsTx();
1044 Mac2PhyStartTx(ack_pkt);
1045}
1046
1048{
1049 int nfree;
1050
1051 Packet *rts_pkt = Packet::alloc();
1053
1054 hdr_OFDM *ofdmph = HDR_OFDM(rts_pkt);
1055
1056 // incrAckPktsTx();
1057
1058 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(rts_pkt);
1059 nfree = pickFreeCarriers(ofdmmac->usage_carriers);
1060 if (nfree > 0)
1061 {
1062 msgDisp.printStatus("", "txRTS", NOW, addr);
1064 RTSsent++;
1065 Mac2PhyStartTx(rts_pkt);
1066 }
1067 else
1068 {
1069 double RTS_Backoff;
1070 double amp = curr_rts_tries > 1 ? (curr_rts_tries / 2) : curr_rts_tries;
1071 if (nextFreeTime > NOW)
1072 RTS_Backoff = abs(nextFreeTime - NOW + ((double)rand() / (RAND_MAX)) * amp);
1073 else
1074 RTS_Backoff = abs(((double)rand() / (RAND_MAX)) * amp);
1075
1076 RTS_Backoff = RTS_Backoff == 0 ? ((double)rand() / (RAND_MAX)) : RTS_Backoff;
1077 msgDisp.printStatus("all carriers unavailable, back to Idle. Next RTS in " + std::to_string(RTS_Backoff), "txRTS", NOW, addr);
1078 RTS_timer.schedule(RTS_Backoff);
1080 RTSvalid = false;
1081 Packet::free(rts_pkt);
1082 stateIdle();
1083 }
1084}
1085
1086void UWSmartOFDM::txCTS(int dest_addr, int *otherFree, int brequested)
1087{
1088 int top_car, bot_car;
1089 int top_avoid_car, bot_avoid_car;
1090 int n_match;
1091
1092 Packet *cts_pkt = Packet::alloc();
1093 initPkt(cts_pkt, UWSMARTOFDM_CTS_PKT, dest_addr);
1094 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(cts_pkt);
1095 hdr_OFDM *ofdmph = HDR_OFDM(cts_pkt);
1096
1097 int myFree[data_car];
1098
1099 pickFreeCarriers(myFree);
1100
1101 string myfreecar = std::to_string(NOW) + " UWSmartOFDM (" + std::to_string(addr) + ")::txCTS() MY FREE CARRIERS: ";
1102 string otherfreecar = " INCOMING FREE CARRIERS: ";
1103 string matchingcar = " MATCHING CARRIERS: ";
1104
1105 n_match = matchCarriers(myFree, otherFree, ofdmmac->usage_carriers);
1106
1107 for (int i = 0; i < data_car; i++)
1108 {
1109 myfreecar += std::to_string(myFree[i]) + " ";
1110 otherfreecar += std::to_string(otherFree[i]) + " ";
1111 matchingcar += std::to_string(ofdmmac->usage_carriers[i]) + " ";
1112 }
1114 std::cout << myfreecar << "-" << otherfreecar << "-> " << n_match << matchingcar << std::endl;
1115 if (nextRTS && dest_addr == HDR_MAC(nextRTS)->macSA())
1116 {
1117 nextRTS = 0;
1118 }
1119 if (n_match > 0)
1120 {
1121 double ackOffset = 0;
1123 ackOffset = 0.07;
1124 double tneeded = (8 * (double)brequested / (n_match * bitrateCar)) + ackOffset;
1125 ofdmmac->timeReserved = tneeded;
1126 int tsl_needed = (tneeded / timeslot_length);
1127 // cout << NOW << " UWSmartOFDM (" << addr << ")::txCTS() {TEMP} t needed" << tneeded << " tslotneeded " << tsl_needed << std::endl;
1128 updateOccupancy(ofdmmac->usage_carriers, tsl_needed + 1);
1129 nextFreeTime = NOW + ofdmmac->timeReserved;
1130 msgDisp.printStatus("nextFreeTime=" + std::to_string(nextFreeTime), "txCTS", NOW, addr);
1131 CTSsent++;
1132
1133 Mac2PhyStartTx(cts_pkt);
1134 }
1135 else
1136 {
1137 msgDisp.printStatus("No matching carriers, back to idle", "txCTS", NOW, addr);
1138
1140 Packet::free(cts_pkt);
1141 stateIdle();
1142 }
1143}
1144
1146{
1148 msgDisp.printStatus("", "stateCheckAckExpired", NOW, addr);
1149
1150 map<pktSeqNum, AckTimer>::iterator it_a;
1151 it_a = mapAckTimer.begin();
1152
1155 if (((*it_a).second).isActive())
1156 {
1159 }
1160 else if (((*it_a).second).isExpired())
1161 {
1163 stateBackoff();
1164 }
1165 else
1166 {
1167 cerr << NOW << " UWSmartOFDM (" << addr
1168 << ")::stateCheckAckExpired() ack_timer logical error, current "
1169 "timer state = "
1170 << status_info[curr_state] << endl;
1171 stateIdle();
1172 // exit(1);
1173 }
1174}
1175
1177{
1179
1180 msgDisp.printStatus("", "stateCheckBackoffExpired", NOW, addr);
1181
1184 if (backoff_timer.isActive())
1185 {
1187 stateBackoff();
1188 }
1189 else if (backoff_timer.isExpired())
1190 {
1192 exitBackoff();
1193 stateIdle();
1194 }
1195 else
1196 {
1197 cerr << NOW << " UWSmartOFDM (" << addr
1198 << ")::stateCheckBackoffExpired() backoff_timer logical error, "
1199 "current timer state = "
1200 << status_info[curr_state] << endl;
1201 stateIdle();
1202 // exit(1);
1203 }
1204}
1205
1207{
1209
1210 msgDisp.printStatus("", "stateCheckCTSBackoffExpired", NOW, addr);
1211
1214 if (CTS_timer.isActive())
1215 {
1217 stateWaitCTS();
1218 }
1219 else if (CTS_timer.isExpired())
1220 {
1224 stateSendRTS();
1225 }
1226 else
1227 {
1228 cerr << NOW << " UWSmartOFDM (" << addr
1229 << ")::stateCheckCTSBackoffExpired() CTS_timer logical error, "
1230 "current timer state = "
1231 << status_info[curr_state] << endl;
1232 stateIdle();
1233 // exit(1);
1234 }
1235}
1236
1238{
1239 Packet *next_p;
1240 mapAckTimer.clear();
1242 int freec[data_car];
1244
1247
1248 msgDisp.printStatus("queue_size=" + std::to_string(mapPacket.size()), "stateIdle", NOW, addr);
1249
1250 if (!mapPacket.empty() && ((mapPacket.size() > 0) || car_assigned) && current_rcvs == 0)
1251 {
1252
1253 map<pktSeqNum, Packet *>::iterator it_p;
1254 it_p = mapPacket.begin();
1255 next_p = (*it_p).second;
1256
1257 hdr_mac *mach = HDR_MAC(next_p);
1258 current_macDA = mach->macDA();
1259 // If carriers assignment is still valid just send data, else ask for more
1260 if (!car_assigned && RTSvalid)
1261 {
1262 msgDisp.printStatus("car_assigned = FALSE sending RTS", "stateIdle", NOW, addr);
1264 stateSendRTS();
1265 }
1266 else if (car_assigned)
1267 {
1268 msgDisp.printStatus("New data but car_assigned = TRUE", "stateIdle", NOW, addr);
1271 stateTxData();
1272 }
1273 else
1274 {
1275 msgDisp.printStatus("New data but RTSvalid = FALSE", "stateIdle", NOW, addr);
1276 }
1277 }
1278 else if (nextRTS && ((NOW - nextRTSts) < 1.5) && !current_rcvs && (pickFreeCarriers(freec) > 0))
1279 {
1283 msgDisp.printStatus("CTS from IDLE", "stateIdle", NOW, addr);
1284 }
1285}
1286
1288{
1290 {
1293
1295 {
1297 cout << NOW << " UWSmartOFDM (" << addr << ")::stateSendRTS() max_tries " << max_rts_tries << " curr_tries " << curr_rts_tries << std::endl;
1298 curr_rts_tries = 0;
1299 msgDisp.printStatus("Going back to Idle, rts_tries > max", "stateSendRTS", NOW, addr);
1300
1305
1306 map<pktSeqNum, Packet *>::iterator it_p;
1307 it_p = mapPacket.begin();
1308 curr_data_pkt = (*it_p).second;
1309 msgDisp.printStatus("Dropping Packet seq_num " + std::to_string(getPktSeqNum(curr_data_pkt)), "stateSendRTS", NOW, addr);
1311
1312 incrDroppedPktsTx();
1313 stateIdle();
1314 }
1315 else
1316 {
1317 msgDisp.printStatus("Sending RTS", "stateSendRTS", NOW, addr);
1320 txRTS();
1321 }
1322 }
1323}
1325{
1328
1329 if (current_rcvs > 0)
1330 {
1331 current_rcvs = 0;
1333 cout << NOW << " UWSmartOFDM (" << addr << ")::stateRxRTS() Interrupting previous receptions " << endl;
1334 }
1335
1336 msgDisp.printStatus("RTS received", "stateRxRTS", NOW, addr);
1338 stateSendCTS(p);
1339
1340 // stateIdle();
1341}
1342
1344{
1345 CTS_timer.force_cancel();
1348 msgDisp.printStatus(" ", "stateRxCTS", NOW, addr);
1349 RTSvalid = true;
1350
1351 hdr_mac *mach = HDR_MAC(p);
1352
1353 nextAssignment = 50000;
1354
1355 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(p);
1356 int slots = ofdmmac->timeReserved / timeslot_length;
1357 updateOccupancy(ofdmmac->usage_carriers, slots + 1);
1359
1360 double newNextFreeT = NOW + ofdmmac->timeReserved;
1361 if (newNextFreeT > nextFreeTime)
1362 nextFreeTime = newNextFreeT;
1363
1364 car_assigned = true;
1365
1366 for (int i = 0; i < mac_carVec.size(); i++)
1367 mac_carVec[i] = 0;
1368
1369 for (int i = 0; i < data_car; i++)
1370 {
1371 int val = ofdmmac->usage_carriers[i];
1372 if (val >= 0)
1373 {
1374 mac_carVec[val] = 1;
1375 }
1376 }
1377 int freec[data_car];
1378 if (current_rcvs == 0 && !mapPacket.empty() && pickFreeCarriers(freec) > 0)
1379 {
1380 string txcarriers = "Going to transmit. mac_carVec = ";
1381 for (int i = 0; i < mac_carVec.size(); i++)
1382 {
1383 txcarriers += std::to_string(mac_carVec[i]);
1384 txcarriers += " ";
1385 }
1386 msgDisp.printStatus(txcarriers, "stateRxCTS", NOW, addr);
1387
1389 stateTxData();
1390 }
1391 else if ((mapPacket.empty() && current_rcvs == 0) || (current_rcvs == 0 && pickFreeCarriers(freec) <= 0))
1392 {
1393 stateIdle();
1394 msgDisp.printStatus("Packet queue empty, back to Idle", "stateRxCTS", NOW, addr);
1395 }
1396 else
1397 {
1398 msgDisp.printStatus("Other receptions ongoing, just keep doing them", "stateRxCTS", NOW, addr);
1399 }
1400}
1401
1403{
1406
1407 msgDisp.printStatus("", "stateSendCTS", NOW, addr);
1408
1411
1412 hdr_mac *mach = HDR_MAC(p);
1413 int dst_addr = mach->macSA();
1414 hdr_cmn *ch = hdr_cmn::access(p);
1415
1416 hdr_OFDMMAC *ofdmmac = HDR_OFDMMAC(p);
1417 waitPkt = (ofdmmac->bytesToSend) / DATA_size;
1418 txCTS(dst_addr, ofdmmac->usage_carriers, ofdmmac->bytesToSend);
1419}
1420
1422{
1424
1425 msgDisp.printStatus("", "stateWaitCTS", NOW, addr);
1428}
1429
1431{
1432 double CTSBackoff = ((double)rand() / (RAND_MAX)) / 1.6 * (curr_rts_tries);
1433 CTSBackoff = CTSBackoff + 0.16;
1434 CTS_timer.force_cancel();
1436 RTSvalid = false;
1437
1438 msgDisp.printStatus("SCHEDULING CTS BACKOFF of " + std::to_string(CTSBackoff), "stateBackoffCTS", NOW, addr);
1439 CTS_timer.schedule(CTSBackoff);
1440
1443}
1444
1452
1454{
1455 backoff_timer.force_cancel();
1457
1458 if (backoff_timer.isFrozen())
1460 else if (!bt)
1462 else
1464
1465 msgDisp.printStatus("", "stateBackoff", NOW, addr);
1466
1469}
1470
1479
1481{
1483
1484 msgDisp.printStatus("", "stateTxData", NOW, addr);
1485
1488
1489 map<pktSeqNum, Packet *>::iterator it_p;
1490 it_p = mapPacket.begin();
1491 curr_data_pkt = (*it_p).second;
1492 int seq_num;
1493 seq_num = getPktSeqNum(curr_data_pkt);
1494 map<pktSeqNum, AckTimer>::iterator it_a;
1495
1496 if (seq_num != last_sent_data_id)
1497 {
1498 putAckTimerInMap(seq_num);
1499 it_a = mapAckTimer.find(seq_num);
1502 ((*it_a).second).resetCounter();
1503 hdr_mac *mach = HDR_MAC(curr_data_pkt);
1504 hdr_MPhy *ph = HDR_MPHY(curr_data_pkt);
1505 hdr_OFDM *ofdmph = HDR_OFDM(curr_data_pkt);
1506 start_tx_time = NOW; // we set curr RTT
1507 last_sent_data_id = seq_num;
1508 if (fullBand == false)
1509 {
1510 for (std::size_t i = 0; i < mac_carVec.size(); ++i)
1511 ofdmph->carriers[ctrl_car + i] = mac_carVec[i];
1512 }
1513 else
1514 {
1515 for (std::size_t i = 0; i < mac_ncarriers; ++i)
1516 ofdmph->carriers[i] = 1;
1517 }
1518 txData();
1519 }
1520 else
1521 {
1522 if (mapAckTimer.size() == 0)
1523 {
1524 putAckTimerInMap(seq_num);
1525 it_a = mapAckTimer.find(seq_num);
1526 ((*it_a).second).resetCounter();
1530 {
1531 hdr_mac *mach = HDR_MAC(curr_data_pkt);
1532 start_tx_time = NOW; // we set curr RTT
1533 last_sent_data_id = seq_num;
1534 hdr_MPhy *ph = HDR_MPHY(curr_data_pkt);
1535 hdr_OFDM *ofdmph = HDR_OFDM(curr_data_pkt);
1536 if (fullBand == false)
1537 {
1538 for (std::size_t i = 0; i < mac_carVec.size(); ++i)
1539 ofdmph->carriers[ctrl_car + i] = mac_carVec[i];
1540 }
1541 else
1542 {
1543 for (std::size_t i = 0; i < mac_ncarriers; ++i)
1544 ofdmph->carriers[i] = 1;
1545 }
1546 txData();
1547 }
1548 else
1549 {
1550 eraseItemFromPktQueue(seq_num);
1551 incrDroppedPktsTx();
1552
1554
1555 string s = "curr_tx_rounds " + std::to_string(curr_tx_rounds) +
1556 " > max_tx_tries = " + std::to_string(max_tx_tries);
1557 msgDisp.printStatus(s, "stateTxData", NOW, addr);
1558
1560 stateIdle();
1561 }
1562 }
1563 else
1564 {
1567 }
1568 }
1569}
1570
1572{
1573
1574 map<pktSeqNum, AckTimer>::iterator it_a;
1575 it_a = mapAckTimer.begin();
1576
1577 ((*it_a).second).stop();
1579
1580 msgDisp.printStatus("", "stateWaitAck", NOW, addr);
1583
1584 ((*it_a).second).incrCounter();
1585 ((*it_a).second).schedule(ACK_timeout + 2 * wait_constant);
1586}
1587
1595
1596void UWSmartOFDM::stateTxAck(int dest_addr)
1597{
1599 ackToSend = false;
1600
1601 msgDisp.printStatus("dest_addr = " + std::to_string(dest_addr), "stateTxAck", NOW, addr);
1602
1605
1606 txAck(dest_addr);
1607}
1608
1609void UWSmartOFDM::stateRxData(Packet *data_pkt)
1610{
1611 ack_timer.stop();
1612 DATA_timer.force_cancel();
1613 msgDisp.printStatus("DATA_timer canceled because DATA received", "stateRxData", NOW, addr);
1614
1616
1618
1619 hdr_mac *mach = HDR_MAC(data_pkt);
1620 int dst_addr = mach->macSA();
1621
1622 hdr_cmn *ch = hdr_cmn::access(data_pkt);
1623 packet_t rx_pkt_type = ch->ptype();
1624 recv_data_id = ch->uid();
1625 ch->size() = ch->size() - HDR_size;
1626 incrDataPktsRx();
1627 waitPkt -= 1;
1628
1629 sendUp(data_pkt);
1630
1632 {
1633 // TO DO: need to change this code to handle multiple receptions
1634 // if you want to use acks: What happens if data packet received, other receptions happening
1635 // but you want to send an ACK?
1636 if (current_rcvs == 0)
1637 {
1639 stateTxAck(dst_addr);
1640 }
1641 else
1642 {
1643 ackToSend = true;
1644 pkt_to_ack = data_pkt;
1645 }
1646 }
1647 else if (current_rcvs == 0)
1648 {
1649 if (waitPkt)
1650 stateBackoff(0.0002);
1651 else
1652 stateIdle();
1653 }
1654 else
1655 {
1657 }
1658}
1659
1661{
1662
1663 map<pktSeqNum, AckTimer>::iterator it_a;
1664 it_a = mapAckTimer.begin();
1665
1666 ((*it_a).second).stop();
1667
1670
1671 msgDisp.printStatus("", "stateRxAck", NOW, addr);
1672
1673 int seq_num;
1674 seq_num = getPktSeqNum(p);
1675 Packet::free(p);
1676 eraseItemFromPktQueue(seq_num);
1677
1678 eraseItemFrommapAckTimer(seq_num);
1680 incrAckPktsRx();
1681 if (current_rcvs == 0)
1682 stateIdle();
1683 else
1685}
1686
1688{
1691
1692 msgDisp.printStatus("", "stateWaitData", NOW, addr);
1694}
1695
1697{
1698 // if (uwsmartofdm_debug)
1699 cout << NOW << " UWSmartOFDM (" << addr << ")::printStateInfo() "
1700 << "from " << status_info[prev_state] << " to "
1702 << ". Reason: " << reason_info[last_reason] << endl;
1703
1704 // if (curr_state == UWSMARTOFDM_STATE_BACKOFF) {
1705 // fout << left << setw(10) << NOW << " UWSmartOFDM (" << addr
1706 // << ")::printStateInfo() "
1707 // << "from " << status_info[prev_state] << " to "
1708 // << status_info[curr_state]
1709 // << ". Reason: " << reason_info[last_reason]
1710 // << ". Backoff duration = " << delay << endl;
1711 // } else {
1712 // fout << left << setw(10) << NOW << " UWSmartOFDM (" << addr
1713 // << ")::printStateInfo() "
1714 // << "from " << status_info[prev_state] << " to "
1715 // << status_info[curr_state]
1716 // << ". Reason: " << reason_info[last_reason] << endl;
1717 // }
1718}
1719
1721{
1722 std::string response;
1723 std::cout << "Press Enter to continue";
1724 std::getline(std::cin, response);
1725}
1726// Remove invalid carriers
1728{
1729 for (int i = 0; i < nouse_carriers.size(); i++)
1730 if (nouse_carriers[i] == c)
1731 nouse_carriers.erase(nouse_carriers.begin() + i);
1732 return;
1733}
1734
1735// Update Interf Table with a new unrecognized packet
1737{
1738 double old_thr = 10.0;
1739 int broken_thr = 2;
1740 std::vector<int> new_nouse;
1741 if (!fullBand)
1742 {
1743 for (int i = 0; i < mac_ncarriers; i++)
1744 {
1745 for (int j = 1; j < interf_table[i].size(); j++)
1746 {
1747 if ((NOW - interf_table[i][j]) > old_thr)
1748 interf_table[i].erase(interf_table[i].begin() + j);
1749 }
1750 }
1751 for (int i = 0; i < mac_ncarriers; i++)
1752 {
1753 if (HDR_OFDM(p)->carriers[i] == 1)
1754 interf_table[i].push_back(NOW);
1755 }
1756 for (int i = 0; i < mac_ncarriers; i++)
1757 {
1758 if (interf_table[i].size() > (broken_thr + 1))
1759 {
1760 new_nouse.push_back(i);
1761 msgDisp.printStatus(to_string(i) + " Added to InterfTable", "updateInterfTable", NOW, addr);
1762 }
1763 }
1764 nouse_carriers = new_nouse;
1765 std::string st = "nouse_carriers : ";
1766 for (int i = 0; i < nouse_carriers.size(); i++)
1767 {
1768 st += std::to_string(nouse_carriers[i]) + " ";
1769 }
1770 msgDisp.printStatus(st, "updateInterfTable", NOW, addr);
1771 }
1772}
1773
1774// IMPORTANT NOTE: since I decided that the LOW prio nodes take double the bandwidth divided
1775// by the number of nodes, the bandwidth is used if there is already a user. Change the
1776// prev_busy parameter if it's decided to use more bandwidth
1777void UWSmartOFDM::carToBeUsed(criticalLevel c, int &top, int &bottom, int &avoid_top, int &avoid_bottom)
1778{
1779 // currently statistics not implemented
1780 avoid_top = 0;
1781 avoid_bottom = 0;
1782 int i = 0;
1783 int carToGive; // num of carriers to give away
1784 int assigned_done = 0;
1785 int prev_busy = 2;
1786
1787 if (c == HIGH)
1788 {
1789 carToGive = floor(data_car / nodeNum);
1790
1792 cout << NOW << " UWSmartOFDM (" << addr << ")::carToBeUsed() for HIGH prio " << carToGive << endl;
1793
1794 for (i = ctrl_car; i < mac_ncarriers; i++)
1795 if (mac_carVec[i] == 0) // Free carrier
1796 {
1797 if (i < (mac_ncarriers - carToGive)) // There are enough carriers to give
1798 {
1799 bottom = i;
1800 top = bottom + carToGive - 1;
1801 assigned_done = 1;
1802 break;
1803 }
1804 }
1805 if (!assigned_done)
1806 {
1807 bottom = ctrl_car;
1808 top = bottom + carToGive - 1;
1809 }
1810 }
1811 else
1812 { // priority is LOW
1813
1814 carToGive = 3 * floor(data_car / nodeNum);
1815
1817 cout << NOW << " UWSmartOFDM (" << addr << ")::carToBeUsed() for LOW prio " << carToGive << endl;
1818
1819 for (i = mac_ncarriers - 1; i >= 0; i--)
1820 if (mac_carVec[i] <= prev_busy) // Free carrier or used only once
1821 {
1822 if (i >= (carToGive + ctrl_car)) // There are enough carriers to give
1823 {
1824 top = i;
1825 bottom = top - carToGive + 1;
1826 assigned_done = 1;
1827 break;
1828 }
1829 }
1830 if (!assigned_done)
1831 {
1832 top = mac_ncarriers;
1833 bottom = top - carToGive + 1;
1834 }
1835 }
1837 cout << NOW << " UWSmartOFDM (" << addr << ")::carToBeUsed() end of top_car is " << top << " bottom_car is " << bottom << endl;
1838
1839 // fill the vector with the used carriers
1840 for (i = bottom; i <= top; i++)
1841 mac_carVec[i]++;
1842}
1843
1845{
1846
1847 int nextFree = 0;
1848 for (int i = 0; i < data_car; i++)
1849 freeCar[i] = -1;
1850
1851 int curTSlot = 0;
1852 int j;
1853 otabmtx.lock();
1854 for (int i = 0; i < data_car; i++)
1855 {
1856 if (occupancy_table[i][oTableIndex] == 0)
1857 {
1858 freeCar[nextFree] = i;
1859 nextFree++;
1860 }
1861 }
1862 otabmtx.unlock();
1863 return nextFree;
1864}
1865
1866int UWSmartOFDM::matchCarriers(int *myFree, int *otherFree, int *matching)
1867{
1868 int mindex = 0;
1869 int foundCar = 0;
1870 msgDisp.printStatus("", "matchCarriers", NOW, addr);
1871 for (int i = 0; (i < data_car) && (foundCar < max_car_reserved); i++)
1872 {
1873 for (int j = 0; (j < data_car) && (foundCar < max_car_reserved); j++)
1874 {
1875 if ((myFree[i] == otherFree[j]) && (myFree[i] != -1))
1876 {
1877 matching[mindex] = myFree[i];
1878 foundCar++;
1879 if (mindex == (data_car - 1))
1880 return foundCar;
1881 else
1882 mindex++;
1883 }
1884 }
1885 }
1886 for (int k = mindex; k < data_car; k++)
1887 matching[k] = -1;
1888 return foundCar;
1889}
1890
1891void UWSmartOFDM::updateOccupancy(int *busyCar, int ntslots)
1892{
1893 // start from the right point in the table
1894 otabmtx.lock();
1895 string st = "";
1896 for (int i = 0; i < data_car; i++)
1897 {
1898 if (busyCar[i] >= 0)
1899 {
1900 for (int j = 0; j < ntslots; j++)
1901 occupancy_table[busyCar[i]][(oTableIndex + j) % timeslots] = 1;
1902 }
1903 }
1904 otabmtx.unlock();
1905 printOccTable();
1906}
1907
1909{
1910 otabmtx.lock();
1911 for (int i = 0; i < data_car; i++)
1913 for (int i = 0; i < nouse_carriers.size(); i++)
1917 otabmtx.unlock();
1918}
1919
1921{
1922 car_assigned = false;
1924 std::cout << NOW << " UWSmartOFDM (" << addr << ")::resetAssignment: car_assignment = FALSE " << std::endl;
1925}
1926
1928{
1929 string st = "";
1930 for (int i = 0; i < data_car; i++)
1931 {
1932 for (int j = 0; j < timeslots; j++)
1933 st = st + std::to_string(occupancy_table[i][j]);
1934 st = st + '\n';
1935 }
1937 {
1938 std::cout << NOW << " UWSmartOFDM (" << addr << ")::Occupancy Table: (current oTableIndex " << oTableIndex << ")" << std::endl;
1939 std::cout << st << std::endl;
1940 }
1941}
1942
1943void UWSmartOFDM::Mac2PhySetTxBusy(int busy, int get)
1944{
1946 if (get == 1)
1947 {
1948 m.setGetOp(1);
1949 }
1950 else
1951 {
1952 m.setTxBusy(busy);
1953 }
1954 sendSyncClMsg(&m);
1955}
1956
1958{
1959
1960 if ((mapPacket.size() > 0) || batch_sending)
1961 return true;
1962 else
1963 return false;
1964}
ClMsgUwPhyTxBusy should be and used to ask either to set or get the transmitting busy variable of a s...
void setGetOp(int)
method to return the transmitting power
void setTxBusy(int powr)
method to set the transmitting busy variable
void initDisplayer(int n, std::string pn, int pactive)
void printStatus(std::string st, std::string fxName, double now, int addr)
Class that describe the binding with tcl scripting language.
TclObject * create(int, const char *const *)
UWSMARTOFDMModuleClass()
Constructor of the class.
virtual void expire(Event *e)
What a node is going to do when a timer expire.
virtual void expire(Event *e)
What a node is going to do when a timer expire.
virtual void expire(Event *e)
What a node is going to do when a timer expire.
virtual void expire(Event *e)
What a node is going to do when a timer expire.
virtual void expire(Event *e)
What a node is going to do when a timer expire.
virtual void stop()
Stop the timer any way.
UWSmartOFDM *UWSMARTOFDM_TIMER_STATUS timer_status
< Pointer of UWSmartOFDM module.
void resetCounter()
Reset the timer counter.
double getDuration()
This methods provide the duration of a timer.
void incrCounter()
Increment the timer counter.
int getCounter()
It provides, how many times a timer ran.
bool isActive()
It tells whether the timer is active or not.
bool isFrozen()
It tells whether the timer is in freeze mode or not.
bool isExpired()
Tells whether the timer is expired or not.
virtual void schedule(double val)
Schedule the time, i.e., how long a timer is going to run.
virtual void freeze()
It freezes or in another word, it stops the timer for some time.
virtual void unFreeze()
It starts the timer from where it was stopped.
This is the base class of UWSmartOFDM protocol, which is a derived class of MMac.
virtual void stateWaitCTS()
Node is in waitCTS state.
void eraseItemFromPktQueue(int seq_num)
It erases the packet from the container.
virtual void stateTxData()
If a node has packet to transmits.
virtual ~UWSmartOFDM()
Destructor of UWSmartOFDM Class.
double wait_constant
This fixed time is used to componsate different time variations.
int recv_data_id
The sequence number of the packet which is received.
virtual void stateRxBackoff()
If a node start receiving a packet when it is in backoff state.
bool print_transitions
Whether to print the state of the nodes.
virtual void Phy2MacEndTx(const Packet *p)
It infroms that a packet transmission end.
void putAckTimerInMap(int seq_num)
Put acknowledgement timer in the container.
virtual double computeTxTime(UWSMARTOFDM_PKT_TYPE type)
Compute the transmission time of a packet.
virtual void recvFromUpperLayers(Packet *p)
This function receives the packet from upper layer and save it in the queue.
virtual void stateRxRTS(Packet *p)
int getHighPrioPktsSent()
std::vector< int > mac_carVec
virtual void incrCurrTxRounds()
Increments the current transmission round of a packet.
void init_macofdm_node(int subCarNum, double carSize, int ctrl_subCar, std::string modulation)
int txsn
Sequence number of the packet which is transmitted.
virtual void txAck(int dest_addr)
This methods transmits ACK packet from MAC layer to PHY layer.
bool has_buffer_queue
Whether the node has buffer to store data or not.
AssignmentValidTimer assignment_valid_timer
An object of the assignment valid timer class.
virtual void stateBackoffCTS()
Node is in BackoffCTS state.
int max_payload
Maximum number of payload in a packet.
void clearOccTable()
clears the carriers used in the past moves the index for the current time to the next slot
CTSTimer CTS_timer
An object of the CTS timer class.
Packet * pkt_to_ack
int HDR_size
Size of the HDR if any.
int uwsmartofdm_debug
Debuging Flag.
void printOccTable()
prints on terminal the table
void addInvalidCarriers(int c)
void carToBeUsed(criticalLevel c, int &top, int &bottom, int &avoid_top, int &avoid_bottom)
returns the current free carriers that can be given to a node top and bottom give the range avoid_top...
virtual double getBackoffTime()
This function calculates the backoff duration and return the backoff time.It employs the exponential ...
Packet * curr_data_pkt
Pointer of the latest selected data packet.
double mac_carrierSize
int RTS_size
Size of the ACK, if the node uses SMARTOFDM.
void updateOccupancy(int *busyCar, int ntslots)
updates occupancy table
UWSmartOFDM()
Constructor of UWSmartOFDM Class.
std::vector< std::vector< int > > occupancy_table
virtual void resetCurrTxRounds()
If a node is going to transmit a new packet, it resets the tx counter.
void putPktInQueue(Packet *p)
A node receives packet(s) from upper layer and store them in the container.
virtual void updateRTT(double rtt)
Update the Round Trip Time (RTT) which is necessary to compute the acknowledgement duration as well a...
AssignmentTimer assignment_timer
An object of the assignment timer class.
static map< UWSMARTOFDM_REASON_STATUS, string > reason_info
Container which stores all the reason information.
virtual void stateRxData(Packet *p)
It process the packet which is received.
virtual void incrUpperDataRx()
Increment the number of Data packet receive for the upper layer.
virtual void txCTS(int dest_addr, int *rcv_car, int bytesToSend)
This methods transmits CTS packet from MAC layer to PHY layer.
std::vector< std::vector< double > > interf_table
AckTimer ack_timer
An object of the AckTimer class.
DATATimer DATA_timer
An object of the DATA timer class.
int last_data_id_rx
The sequence number of last received packet.
void removeInvalidCarrier(int c)
virtual void stateRxAck(Packet *p)
The node comes to this state if it receives an ACK packet.
void updateInterfTable(Packet *p)
virtual void stateWaitData(double t)
@ UWSMARTOFDM_STATE_BACKOFF
@ UWSMARTOFDM_STATE_RX_IDLE
@ UWSMARTOFDM_STATE_DATA_RX
@ UWSMARTOFDM_STATE_CHK_CTS_BACKOFF_TIMEOUT
@ UWSMARTOFDM_STATE_CHK_BACKOFF_TIMEOUT
@ UWSMARTOFDM_STATE_CHK_ACK_TIMEOUT
@ UWSMARTOFDM_STATE_WAIT_ACK
@ UWSMARTOFDM_STATE_RX_BACKOFF
@ UWSMARTOFDM_STATE_CTRL_BACKOFF
@ UWSMARTOFDM_STATE_TX_DATA
@ UWSMARTOFDM_STATE_TX_ACTIVE
@ UWSMARTOFDM_STATE_WRONG_PKT_RX
@ UWSMARTOFDM_STATE_WAIT_CTS
@ UWSMARTOFDM_STATE_RX_WAIT_ACK
@ UWSMARTOFDM_STATE_RX_ACTIVE
@ UWSMARTOFDM_STATE_WAIT_DATA
ofstream fout
An object of ofstream class.
int getPktSeqNum(Packet *p)
This method is used to get the sequence number from a packet.
int rttsamples
Number of RTT samples.
virtual void updateAckTimeout(double rtt)
Like updateRTT() function.
double max_backoff_counter
Maximum number of backoff it will consider while it increases the backoff exponentially.
static map< UWSMARTOFDM_STATUS, string > status_info
Container which stores all the status information.
virtual void stateBackoff(double bt=0)
If ACK packet is not received within the acknowledgement expire time.
virtual void Phy2MacEndRx(Packet *p)
PHY layer informs the MAC layer that the reception of the packet is over.
double start_tx_time
Time when a packet start transmitting.
UWSMARTOFDM_STATUS curr_state
Enum variable.
virtual void Phy2MacStartRx(const Packet *p)
PHY layer informs the MAC layer that it is receiving a packet.
virtual void stateSendCTS(Packet *p)
Node is in sendRTS state.
virtual void initInfo()
This function is used to initialize the UWSmartOFDM protocol.
virtual void stateCheckCTSBackoffExpired()
It checks whether the CTS backoff timer is already expired while it was busy with other activities.
double sumrtt2
Sum of (RTT^2)
UWSMARTOFDM_STATUS prev_state
Enum variable.
std::vector< string > mac_carMod
int matchCarriers(int *myFree, int *otherFree, int *matching)
Returns free Carriers matching between itself and the sender to be used when an RTS is received to fi...
virtual int command(int argc, const char *const *argv)
TCL command interpreter.
static bool initialized
It checks whether UWSmartOFDM protocol is initialized or not.
virtual void stateIdle()
Node is in Idle state.
BackOffTimer backoff_timer
An object of the backoff timer class.
double nextAssignment
double srtt
Smoothed Round Trip Time, calculated as for TCP.
virtual void Mac2PhyStartTx(Packet *p)
It informs that a packet transmission started.
void eraseItemFrommapAckTimer(int seq_num)
Erase an item from acknowledgement stored container.
virtual void refreshReason(UWSMARTOFDM_REASON_STATUS reason)
To know the reason why a node is in this current state.
static const double prop_speed
Speed of the sound signal.
double timeslot_length
map< pktSeqNum, Packet * > mapPacket
Container where Data packets are stored.
void resetAssignment()
resets value of car_assigned to FALSE
std::mutex otabmtx
std::atomic< int > current_rcvs
double alpha_
This variable is used to tune the RTT.
int getHighPrioPktsRecv()
double ACK_timeout
ACK timeout for the initial packet.
double sumrtt
Sum of RTT samples.
int ACK_size
Size of the ACK, if the node uses ARQ technique.
int buffer_pkts
Number of packets a node can store in the container.
int last_sent_data_id
sequence number of the last sent packet
virtual void txData()
This method transmits Data packets from MAC layer to PHY layer.
double nextFreeTime
virtual void initPkt(Packet *p, UWSMARTOFDM_PKT_TYPE pkt_type, int dest_addr=0)
This method, initialize the packet.
virtual void stateTxAck(int dest_addr)
If the protocl uses ARQ technique, in that case, after receiving a Data packet the node sends an ACK ...
UWSMARTOFDM_STATUS prev_prev_state
Enum variable.
int CTS_size
Size of the ACK, if the node uses SMARTOFDM.
virtual void stateRxCTS(Packet *p)
int DATA_size
Size of the DATA packet, if the node uses SMARTOFDM.
virtual void stateCheckAckExpired()
It checks whether the ack timer is already expired while it was busy with other activities.
@ UWSMARTOFDM_REASON_DATA_EMPTY
@ UWSMARTOFDM_REASON_ACK_RX
@ UWSMARTOFDM_REASON_ACK_TX
@ UWSMARTOFDM_REASON_START_RX
@ UWSMARTOFDM_REASON_RTS_RX
@ UWSMARTOFDM_REASON_ACK_TIMEOUT
@ UWSMARTOFDM_REASON_PKT_NOT_FOR_ME
@ UWSMARTOFDM_REASON_CTS_BACKOFF_TIMEOUT
@ UWSMARTOFDM_REASON_WAIT_DATA
@ UWSMARTOFDM_REASON_BACKOFF_TIMEOUT
@ UWSMARTOFDM_REASON_DATA_PENDING
@ UWSMARTOFDM_REASON_PHY_LAYER_SENDING
@ UWSMARTOFDM_REASON_MAX_RTS_TRIES
@ UWSMARTOFDM_REASON_DATAT_EXPIRED
@ UWSMARTOFDM_REASON_CTS_TX
@ UWSMARTOFDM_REASON_MAX_TX_TRIES
@ UWSMARTOFDM_REASON_BACKOFF_PENDING
@ UWSMARTOFDM_REASON_DATA_RX
@ UWSMARTOFDM_REASON_WAIT_CTS_PENDING
@ UWSMARTOFDM_REASON_PHY_LAYER_RECEIVING
@ UWSMARTOFDM_REASON_NOT_SET
@ UWSMARTOFDM_REASON_RTS_TX
@ UWSMARTOFDM_REASON_CTS_RX
@ UWSMARTOFDM_REASON_DATA_TX
@ UWSMARTOFDM_REASON_WAIT_ACK_PENDING
@ UWSMARTOFDM_REASON_PKT_ERROR
@ UWSMARTOFDM_REASON_PREVIOUS_RTS
@ UWSMARTOFDM_REASON_DATA_NOCAR
@ UWSMARTOFDM_REASON_DATA_CARASSIGNED
virtual void refreshState(UWSMARTOFDM_STATUS state)
Refreshes the states of the node.
map< pktSeqNum, AckTimer > mapAckTimer
Container where acknowledgement timer(s) is stored.
virtual void stateWaitAck()
After transmitting a Data packet, a node waits for the ACK packet.
std::vector< int > nouse_carriers
virtual void exitBackoff()
It stops the backoff timer.
int curr_tx_rounds
How many times a packet is transmitted.
virtual void waitForUser()
virtual void stateCheckBackoffExpired()
It checks whether the backoff timer is already expired while it was busy with other activities.
double backoff_tuner
Tunes the backoff duration.
MsgDisplayer msgDisp
virtual void printStateInfo(double delay=0)
This methods print the state information of the nodes.
int pickFreeCarriers(int *freeC)
Returns max 5 carriers that are free in the next n time slots from occupancy table.
virtual void stateSendRTS()
Node is in sendRTS state.
virtual void stateRxIdle()
If a node start receiving a packet in Idle state.
static map< UWSMARTOFDM_PKT_TYPE, string > pkt_type_info
Container which stores all the packet type information of UWSmartOFDM.
UWSMARTOFDM_ACK_MODES ack_mode
Enum variable.
void Mac2PhySetTxBusy(int, int get=0)
RTSTimer RTS_timer
An object of the RTS timer class.
virtual void exitCTSBackoff()
It stops the CTS backoff timer.
Packet * nextRTS
UWSMARTOFDM_PKT_TYPE
Enumeration class of UWSmartOFDM packet type.
virtual void stateRxWaitAck()
If a node receives any packet while it was waiting for ACK packet, it moves to this state.
UWSMARTOFDM_REASON_STATUS last_reason
Enum variable which stores the last reason why a node changes its state.
int getUpLayersDataPktsRx()
int max_tx_tries
Maximum number of retransmissions attempt.
virtual void txRTS()
This methods transmits RTS packet from MAC layer to PHY layer.
Header of the OFDM message with fields to implement a multi carrier system.
int usage_carriers[MAX_AVAL_CAR]
int bytesToSend
Vector with available carriers. fields are -1 if no more carriers are available (1 byte for now)
double timeReserved
Header of the OFDM message with fields to implement a multi carrier system.
int carriers[MAX_CARRIERS]
double carrierSize
bool nativeOFDM
string carMod[MAX_CARRIERS]
UWSMARTOFDMModuleClass class_module_uwsmartofdm
@ NOT_SET
@ SESSION_DISTANCE_NOT_SET
Your can find the description of this protocol in the paper, named "A Reservation-based Adaptive MAC ...
#define UWSMARTOFDM_DROP_REASON_ERROR
#define UWSMARTOFDM_DROP_REASON_BUFFER_FULL
#define UWSMARTOFDM_DROP_REASON_WRONG_RECEIVER
criticalLevel
@ HIGH
@ NOT_SET
Definition uwaloha.cpp:44
std::pair< int, int > counter
counter of collisions
#define HDR_OFDMMAC(p)
alias defined to access the PROBE HEADER
#define HDR_OFDM(p)
alias defined to access the PROBE HEADER
Definition of ClMsgUwMmac class.