A Discrete-Event Network Simulator
API
rv-battery-model-test.cc
Go to the documentation of this file.
1/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/*
3 * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 2 as
7 * published by the Free Software Foundation;
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17 *
18 * Author: He Wu <mdzz@u.washington.edu>
19 */
20
21#include "ns3/rv-battery-model.h"
22#include "ns3/wifi-radio-energy-model.h"
23#include "ns3/rv-battery-model-helper.h"
24#include "ns3/wifi-radio-energy-model-helper.h"
25#include "ns3/energy-source-container.h"
26#include "ns3/device-energy-model-container.h"
27#include "ns3/log.h"
28#include "ns3/node.h"
29#include "ns3/simulator.h"
30#include "ns3/double.h"
31#include "ns3/config.h"
32#include "ns3/command-line.h"
33#include "ns3/string.h"
34#include "ns3/yans-wifi-helper.h"
35#include <cmath>
36
37using namespace ns3;
38
39NS_LOG_COMPONENT_DEFINE ("RvBatteryModelTestSuite");
40
55{
56public:
58 virtual ~BatteryLifetimeTest ();
59
66 void CreateLoadProfiles (void);
67
76 bool ConstantLoadTest (double load, Time expLifetime);
77
87 bool VariableLoadTest (std::vector<double> loads,
88 std::vector<Time> timeStamps,
89 Time expLifetime);
90
92 typedef struct LoadProfile
93 {
94 std::vector<double> loads;
95 std::vector<Time> timeStamps;
99
100 std::vector<LoadProfile> m_loadProfiles;
101 double m_alpha;
102 double m_beta;
103};
104
106{
107 // Itsy battery
108 m_alpha = 35220;
109 m_beta = 0.637;
110}
111
113{
114}
115
116void
118{
119 // create set of load profiles
120 LoadProfile profile;
121
122 std::vector<double> loads;
123 std::vector<Time> timeStamps;
124
125 // C1
126 loads.push_back (0.628);
127 loads.push_back (0);
128 loads.push_back (0.628);
129
130 timeStamps.push_back (Seconds (0));
131 timeStamps.push_back (Seconds (19.5 * 60));
132 timeStamps.push_back (Seconds (26.0 * 60));
133
134 profile.loads = loads;
135 profile.timeStamps = timeStamps;
136 profile.itsyLifetime = Seconds (55.0 * 60); // 55.0 minutes
137 profile.dualFoilLifeTime = Seconds (36.2 * 60); // 36.2 minutes
138
139 m_loadProfiles.push_back (profile);
140
141 loads.clear ();
142 timeStamps.clear ();
143
144 // C2
145 loads.push_back (0.4947);
146 loads.push_back (0);
147 loads.push_back (0.4947);
148
149 timeStamps.push_back (Seconds (0));
150 timeStamps.push_back (Seconds (31.0 * 60));
151 timeStamps.push_back (Seconds (41.3 * 60));
152
153 profile.loads = loads;
154 profile.timeStamps = timeStamps;
155 profile.itsyLifetime = Seconds (73.9 * 60); // 73.9 minutes
156 profile.dualFoilLifeTime = Seconds (55.8 * 60); // 55.8 minutes
157
158 m_loadProfiles.push_back (profile);
159
160 loads.clear ();
161 timeStamps.clear ();
162
163 // C3
164 loads.push_back (0.4256);
165 loads.push_back (0);
166 loads.push_back (0.4256);
167
168 timeStamps.push_back (Seconds (0));
169 timeStamps.push_back (Seconds (41.0 * 60));
170 timeStamps.push_back (Seconds (54.6 * 60));
171
172 profile.loads = loads;
173 profile.timeStamps = timeStamps;
174 profile.itsyLifetime = Seconds (88.8 * 60); // 88.8 minutes
175 profile.dualFoilLifeTime = Seconds (71.8 * 60); // 71.8 minutes
176
177 m_loadProfiles.push_back (profile);
178
179 loads.clear ();
180 timeStamps.clear ();
181
182 // C4
183 loads.push_back (0.2923);
184 loads.push_back (0);
185 loads.push_back (0.2923);
186
187 timeStamps.push_back (Seconds (0));
188 timeStamps.push_back (Seconds (74.6 * 60));
189 timeStamps.push_back (Seconds (99.5 * 60));
190
191 profile.loads = loads;
192 profile.timeStamps = timeStamps;
193 profile.itsyLifetime = Seconds (137.8 * 60); // 137.8 minutes
194 profile.dualFoilLifeTime = Seconds (124.9 * 60); // 124.9 minutes
195
196 m_loadProfiles.push_back (profile);
197
198 loads.clear ();
199 timeStamps.clear ();
200
201 // C5
202 loads.push_back (0.2227);
203 loads.push_back (0);
204 loads.push_back (0.2227);
205
206 timeStamps.push_back (Seconds (0));
207 timeStamps.push_back (Seconds (105.7 * 60));
208 timeStamps.push_back (Seconds (140.9 * 60));
209
210 profile.loads = loads;
211 profile.timeStamps = timeStamps;
212 profile.itsyLifetime = Seconds (185.8 * 60); // 185.8 minutes
213 profile.dualFoilLifeTime = Seconds (176.7 * 60); // 176.7 minutes
214
215 m_loadProfiles.push_back (profile);
216
217 loads.clear ();
218 timeStamps.clear ();
219
220 // C6
221 loads.push_back (0.628);
222 loads.push_back (0);
223 loads.push_back (0.628);
224
225 timeStamps.push_back (Seconds (0));
226 timeStamps.push_back (Seconds (19.5 * 60));
227 timeStamps.push_back (Seconds (29.9 * 60));
228
229 profile.loads = loads;
230 profile.timeStamps = timeStamps;
231 profile.itsyLifetime = Seconds (58.9 * 60); // 58.9 minutes
232 profile.dualFoilLifeTime = Seconds (41.0 * 60); // 41.0 minutes
233
234 m_loadProfiles.push_back (profile);
235
236 loads.clear ();
237 timeStamps.clear ();
238
239 // C7
240 loads.push_back (0.628);
241 loads.push_back (0);
242 loads.push_back (0.628);
243
244 timeStamps.push_back (Seconds (0));
245 timeStamps.push_back (Seconds (19.5 * 60));
246 timeStamps.push_back (Seconds (22.1 * 60));
247
248 profile.loads = loads;
249 profile.timeStamps = timeStamps;
250 profile.itsyLifetime = Seconds (51.1 * 60); // 51.1 minutes
251 profile.dualFoilLifeTime = Seconds (30.8 * 60); // 30.8 minutes
252
253 m_loadProfiles.push_back (profile);
254
255 loads.clear ();
256 timeStamps.clear ();
257
258 // C8
259 loads.push_back (0.628);
260 loads.push_back (0);
261 loads.push_back (0.628);
262
263 timeStamps.push_back (Seconds (0));
264 timeStamps.push_back (Seconds (23.4 * 60));
265 timeStamps.push_back (Seconds (29.9 * 60));
266
267 profile.loads = loads;
268 profile.timeStamps = timeStamps;
269 profile.itsyLifetime = Seconds (55.0 * 60); // 55.0 minutes
270 profile.dualFoilLifeTime = Seconds (37.4 * 60); // 37.4 minutes
271
272 m_loadProfiles.push_back (profile);
273
274 loads.clear ();
275 timeStamps.clear ();
276
277 // C9
278 loads.push_back (0.628);
279 loads.push_back (0);
280 loads.push_back (0.628);
281
282 timeStamps.push_back (Seconds (0));
283 timeStamps.push_back (Seconds (15.6 * 60));
284 timeStamps.push_back (Seconds (22.1 * 60));
285
286 profile.loads = loads;
287 profile.timeStamps = timeStamps;
288 profile.itsyLifetime = Seconds (55.0 * 60); // 55.0 minutes
289 profile.dualFoilLifeTime = Seconds (35.2 * 60); // 35.2 minutes
290
291 m_loadProfiles.push_back (profile);
292
293 loads.clear ();
294 timeStamps.clear ();
295
296 // C10
297 loads.push_back (0.300);
298 loads.push_back (0.628);
299 loads.push_back (0.4947);
300 loads.push_back (0.2523);
301 loads.push_back (0.2341);
302 loads.push_back (0.1379);
303 loads.push_back (0.1139);
304 loads.push_back (0.2656);
305
306 timeStamps.push_back (Seconds (0));
307 timeStamps.push_back (Seconds (0.5 * 60));
308 timeStamps.push_back (Seconds (5.5 * 60));
309 timeStamps.push_back (Seconds (10.5 * 60));
310 timeStamps.push_back (Seconds (35.5 * 60));
311 timeStamps.push_back (Seconds (60.5 * 60));
312 timeStamps.push_back (Seconds (85.5 * 60));
313 timeStamps.push_back (Seconds (110.5 * 60));
314
315 profile.loads = loads;
316 profile.timeStamps = timeStamps;
317 profile.itsyLifetime = Seconds (144.3 * 60); // 144.3 minutes
318 profile.dualFoilLifeTime = Seconds (132.6 * 60); // 132.6 minutes
319
320 m_loadProfiles.push_back (profile);
321
322 loads.clear ();
323 timeStamps.clear ();
324
325 // C11
326 loads.push_back (0.300);
327 loads.push_back (0.1139);
328 loads.push_back (0.1379);
329 loads.push_back (0.2341);
330 loads.push_back (0.2523);
331 loads.push_back (0.4947);
332 loads.push_back (0.628);
333 loads.push_back (0.2656);
334
335 timeStamps.push_back (Seconds (0));
336 timeStamps.push_back (Seconds (0.5 * 60));
337 timeStamps.push_back (Seconds (25.5 * 60));
338 timeStamps.push_back (Seconds (50.5 * 60));
339 timeStamps.push_back (Seconds (75.5 * 60));
340 timeStamps.push_back (Seconds (100.5 * 60));
341 timeStamps.push_back (Seconds (105.5 * 60));
342 timeStamps.push_back (Seconds (110.5 * 60));
343
344 profile.loads = loads;
345 profile.timeStamps = timeStamps;
346 profile.itsyLifetime = Seconds (144.3 * 60); // 144.3 minutes
347 profile.dualFoilLifeTime = Seconds (107.4 * 60); // 107.4 minutes
348
349 m_loadProfiles.push_back (profile);
350
351 loads.clear ();
352 timeStamps.clear ();
353
354 // C12
355 loads.push_back (0.300);
356 loads.push_back (0.1139);
357 loads.push_back (0.1379);
358 loads.push_back (0.2341);
359 loads.push_back (0.2523);
360 loads.push_back (0.4947);
361 loads.push_back (0.0);
362 loads.push_back (0.300);
363 loads.push_back (0.628);
364 loads.push_back (0.2656);
365
366 timeStamps.push_back (Seconds (0));
367 timeStamps.push_back (Seconds (0.5 * 60));
368 timeStamps.push_back (Seconds (25.5 * 60));
369 timeStamps.push_back (Seconds (50.5 * 60));
370 timeStamps.push_back (Seconds (75.5 * 60));
371 timeStamps.push_back (Seconds (100.5 * 60));
372 timeStamps.push_back (Seconds (105.5 * 60));
373 timeStamps.push_back (Seconds (130.5 * 60));
374 timeStamps.push_back (Seconds (131.0 * 60));
375 timeStamps.push_back (Seconds (136.0 * 60));
376
377 profile.loads = loads;
378 profile.timeStamps = timeStamps;
379 profile.itsyLifetime = Seconds (169.3 * 60); // 169.3 minutes
380 profile.dualFoilLifeTime = Seconds (155.4 * 60); // 155.4 minutes
381
382 m_loadProfiles.push_back (profile);
383
384 loads.clear ();
385 timeStamps.clear ();
386
387 // C13
388 loads.push_back (0.300);
389 timeStamps.push_back (Seconds (0));
390
391 for (int i = 0; i < 5; i++)
392 {
393 loads.push_back (0.628);
394 loads.push_back (0.4947);
395 loads.push_back (0.2523);
396 loads.push_back (0.2341);
397 loads.push_back (0.1379);
398 loads.push_back (0.1139);
399
400 timeStamps.push_back (Seconds ((0.5 + i * 22.5) * 60));
401 timeStamps.push_back (Seconds ((1.5 + i * 22.5) * 60));
402 timeStamps.push_back (Seconds ((2.5 + i * 22.5) * 60));
403 timeStamps.push_back (Seconds ((7.5 + i * 22.5) * 60));
404 timeStamps.push_back (Seconds ((12.5 + i * 22.5) * 60));
405 timeStamps.push_back (Seconds ((17.5 + i * 22.5) * 60));
406 }
407
408 loads.push_back (0.2656);
409 timeStamps.push_back (Seconds (110.5 * 60));
410
411 profile.loads = loads;
412 profile.timeStamps = timeStamps;
413 profile.itsyLifetime = Seconds (144.3 * 60); // 144.3 minutes
414 profile.dualFoilLifeTime = Seconds (131.7 * 60); // 131.7 minutes
415
416 m_loadProfiles.push_back (profile);
417
418 loads.clear ();
419 timeStamps.clear ();
420
421 // C14, time stamp calculation in paper is off, using our own estimated value
422 loads.push_back (0.300);
423 timeStamps.push_back (Seconds (0));
424
425 for (int i = 0; i < 5; i++)
426 {
427 loads.push_back (0.1139);
428 loads.push_back (0.1379);
429 loads.push_back (0.2341);
430 loads.push_back (0.2523);
431 loads.push_back (0.4947);
432 loads.push_back (0.628);
433
434 timeStamps.push_back (Seconds ((0.5 + i * 22.5) * 60));
435 timeStamps.push_back (Seconds ((5.5 + i * 22.5) * 60));
436 timeStamps.push_back (Seconds ((10.5 + i * 22.5) * 60));
437 timeStamps.push_back (Seconds ((15.5 + i * 22.5) * 60));
438 timeStamps.push_back (Seconds ((20.5 + i * 22.5) * 60));
439 timeStamps.push_back (Seconds ((21.5 + i * 22.5) * 60));
440 }
441
442 loads.push_back (0.2656);
443 timeStamps.push_back (Seconds (112.5 * 60));
444
445 profile.loads = loads;
446 profile.timeStamps = timeStamps;
447 profile.itsyLifetime = Seconds (141.5 * 60); // 141.5 minutes
448 profile.dualFoilLifeTime = Seconds (126.3 * 60); // 126.3 minutes
449
450 m_loadProfiles.push_back (profile);
451
452 loads.clear ();
453 timeStamps.clear ();
454
455 // C15
456 loads.push_back (0.2227);
457 loads.push_back (0.2045);
458 loads.push_back (0.1083);
459 loads.push_back (0.0843);
460 loads.push_back (0.2227);
461
462 timeStamps.push_back (Seconds (0));
463 timeStamps.push_back (Seconds (50.0 * 60));
464 timeStamps.push_back (Seconds (100.0 * 60));
465 timeStamps.push_back (Seconds (150.0 * 60));
466 timeStamps.push_back (Seconds (200.0 * 60));
467
468 profile.loads = loads;
469 profile.timeStamps = timeStamps;
470 profile.itsyLifetime = Seconds (211.4 * 60); // 211.4 minutes
471 profile.dualFoilLifeTime = Seconds (209.2 * 60); // 209.2 minutes
472
473 m_loadProfiles.push_back (profile);
474
475 loads.clear ();
476 timeStamps.clear ();
477
478 // C16
479 loads.push_back (0.0843);
480 loads.push_back (0.1083);
481 loads.push_back (0.2045);
482 loads.push_back (0.2227);
483 loads.push_back (0.2227);
484
485 timeStamps.push_back (Seconds (0));
486 timeStamps.push_back (Seconds (50.0 * 60));
487 timeStamps.push_back (Seconds (100.0 * 60));
488 timeStamps.push_back (Seconds (150.0 * 60));
489 timeStamps.push_back (Seconds (200.0 * 60));
490
491 profile.loads = loads;
492 profile.timeStamps = timeStamps;
493 profile.itsyLifetime = Seconds (211.4 * 60); // 211.4 minutes
494 profile.dualFoilLifeTime = Seconds (200.7 * 60); // 200.7 minutes
495
496 m_loadProfiles.push_back (profile);
497
498 loads.clear ();
499 timeStamps.clear ();
500
501 // C17
502 loads.push_back (0.0843);
503 loads.push_back (0.1083);
504 loads.push_back (0.2045);
505 loads.push_back (0.0);
506 loads.push_back (0.2227);
507 loads.push_back (0.2227);
508
509 timeStamps.push_back (Seconds (0));
510 timeStamps.push_back (Seconds (50.0 * 60));
511 timeStamps.push_back (Seconds (100.0 * 60));
512 timeStamps.push_back (Seconds (150.0 * 60));
513 timeStamps.push_back (Seconds (200.0 * 60));
514 timeStamps.push_back (Seconds (250.0 * 60));
515
516 profile.loads = loads;
517 profile.timeStamps = timeStamps;
518 profile.itsyLifetime = Seconds (261.4 * 60); // 261.4 minutes
519 profile.dualFoilLifeTime = Seconds (251.2 * 60); // 251.2 minutes
520
521 m_loadProfiles.push_back (profile);
522
523 loads.clear ();
524 timeStamps.clear ();
525
526 // C18
527 for (int i = 0; i < 10; i++)
528 {
529 loads.push_back (0.0843);
530 loads.push_back (0.1083);
531 loads.push_back (0.2045);
532 loads.push_back (0.2227);
533
534 timeStamps.push_back (Seconds ((0.0 + i * 20.0) * 60));
535 timeStamps.push_back (Seconds ((5.0 + i * 20.0) * 60));
536 timeStamps.push_back (Seconds ((10.0 + i * 20.0) * 60));
537 timeStamps.push_back (Seconds ((15.0 + i * 20.0) * 60));
538 }
539
540 loads.push_back (0.2227);
541 timeStamps.push_back (Seconds (200.0));
542
543 profile.loads = loads;
544 profile.timeStamps = timeStamps;
545 profile.itsyLifetime = Seconds (211.4 * 60); // 211.4 minutes
546 profile.dualFoilLifeTime = Seconds (204.6 * 60); // 204.6 minutes
547
548 m_loadProfiles.push_back (profile);
549
550 loads.clear ();
551 timeStamps.clear ();
552
553 // C19
554 for (int i = 0; i < 10; i++)
555 {
556 loads.push_back (0.0755);
557 loads.push_back (0.0949);
558 loads.push_back (0.2045);
559 loads.push_back (0.2227);
560
561 timeStamps.push_back (Seconds ((0.0 + i * 20.0) * 60));
562 timeStamps.push_back (Seconds ((5.0 + i * 20.0) * 60));
563 timeStamps.push_back (Seconds ((10.0 + i * 20.0) * 60));
564 timeStamps.push_back (Seconds ((15.0 + i * 20.0) * 60));
565 }
566
567 loads.push_back (0.2227);
568 timeStamps.push_back (Seconds (200.0));
569
570 profile.loads = loads;
571 profile.timeStamps = timeStamps;
572 profile.itsyLifetime = Seconds (216.4 * 60); // 216.4 minutes
573 profile.dualFoilLifeTime = Seconds (208.7 * 60); // 208.7 minutes
574
575 m_loadProfiles.push_back (profile);
576
577 loads.clear ();
578 timeStamps.clear ();
579
580 // C20
581 for (int i = 0; i < 50; i++)
582 {
583 loads.push_back (0.4947);
584 loads.push_back (0.628);
585
586 timeStamps.push_back (Seconds ((0.0 + i * 2.0) * 60));
587 timeStamps.push_back (Seconds ((1.0 + i * 2.0) * 60));
588 }
589
590 profile.loads = loads;
591 profile.timeStamps = timeStamps;
592 profile.itsyLifetime = Seconds (55.3 * 60); // 55.3 minutes
593 profile.dualFoilLifeTime = Seconds (33.2 * 60); // 33.2 minutes
594
595 m_loadProfiles.push_back (profile);
596
597 loads.clear ();
598 timeStamps.clear ();
599
600 // C21
601 for (int i = 0; i < 50; i++)
602 {
603 loads.push_back (0.4947);
604 loads.push_back (0.628);
605 loads.push_back (0.0576);
606
607 timeStamps.push_back (Seconds ((0.0 + i * 3.0) * 60));
608 timeStamps.push_back (Seconds ((1.0 + i * 3.0) * 60));
609 timeStamps.push_back (Seconds ((2.0 + i * 3.0) * 60));
610 }
611
612 profile.loads = loads;
613 profile.timeStamps = timeStamps;
614 profile.itsyLifetime = Seconds (79.6 * 60); // 79.6 minutes
615 profile.dualFoilLifeTime = Seconds (55.9 * 60); // 55.9 minutes
616
617 m_loadProfiles.push_back (profile);
618
619 loads.clear ();
620 timeStamps.clear ();
621
622 // C22
623 for (int i = 0; i < 150; i++)
624 {
625 loads.push_back (0.005 + 0.005 * i);
626 timeStamps.push_back (Seconds ((0.0 + i * 1.0) * 60));
627 }
628
629 profile.loads = loads;
630 profile.timeStamps = timeStamps;
631 profile.itsyLifetime = Seconds (112.2 * 60); // 112.2 minutes
632 profile.dualFoilLifeTime = Seconds (94.5 * 60); // 94.5 minutes
633
634 m_loadProfiles.push_back (profile);
635
636 loads.clear ();
637 timeStamps.clear ();
638}
639
640int
641main (int argc, char **argv)
642{
643 CommandLine cmd (__FILE__);
644 cmd.Parse (argc, argv);
645
646 NS_LOG_DEBUG ("Constant load run.");
647
649 int ret = 0;
650
651 if (test.ConstantLoadTest (0.640, Seconds (2844.0)))
652 {
653 ret = 1;
654 std::cerr << "Problems with constant load test (640mA)." << std::endl;
655 }
656 if (test.ConstantLoadTest (0.320, Seconds (6146.0)))
657 {
658 ret = 1;
659 std::cerr << "Problems with constant load test (320mA)." << std::endl;
660 }
661 if (test.ConstantLoadTest (0.128, Seconds (16052.0)))
662 {
663 ret = 1;
664 std::cerr << "Problems with constant load test (128mA)." << std::endl;
665 }
666 if (test.ConstantLoadTest (0.064, Seconds (32561.0)))
667 {
668 ret = 1;
669 std::cerr << "Problems with constant load test (64mA)." << std::endl;
670 }
671 if (test.ConstantLoadTest (0.032, Seconds (65580.0)))
672 {
673 ret = 1;
674 std::cerr << "Problems with constant load test (32mA)." << std::endl;
675 }
676
677 // create load profiles for variable load test
678 test.CreateLoadProfiles ();
679
680 // variable load with Itsy battery
681 NS_LOG_DEBUG ("\n\nItsy");
682 test.m_alpha = 35220;
683 test.m_beta = 0.637;
684 for (uint32_t i = 0; i < test.m_loadProfiles.size (); i++)
685 {
686 NS_LOG_DEBUG ("========");
687 NS_LOG_DEBUG ("Variable load profile C" << i + 1);
688 if (test.VariableLoadTest (test.m_loadProfiles[i].loads,
689 test.m_loadProfiles[i].timeStamps,
690 test.m_loadProfiles[i].itsyLifetime))
691 {
692 ret = 1;
693 std::cerr << "Problems with variable load test (Itsy)." << std::endl;
694 }
695 }
696
697 // variable load with DUALFOIL battery
698 NS_LOG_DEBUG ("\n\nDUALFOIL");
699 test.m_alpha = 40027;
700 test.m_beta = 0.276;
701 for (uint32_t i = 0; i < test.m_loadProfiles.size (); i++)
702 {
703 NS_LOG_DEBUG ("========");
704 NS_LOG_DEBUG ("Variable load profile C" << i + 1);
705 if (test.VariableLoadTest (test.m_loadProfiles[i].loads,
706 test.m_loadProfiles[i].timeStamps,
707 test.m_loadProfiles[i].dualFoilLifeTime))
708 {
709 ret = 1;
710 std::cerr << "Problems with variable load test (DUALFOIL)." << std::endl;
711 }
712 }
713
714 return ret;
715}
716
717bool
719{
720 // create single node
722 c.Create (1);
723
724 std::string phyMode ("DsssRate1Mbps");
725
726 // disable fragmentation for frames below 2200 bytes
727 Config::SetDefault ("ns3::WifiRemoteStationManager::FragmentationThreshold",
728 StringValue ("2200"));
729 // turn off RTS/CTS for frames below 2200 bytes
730 Config::SetDefault ("ns3::WifiRemoteStationManager::RtsCtsThreshold",
731 StringValue ("2200"));
732 // Fix non-unicast data rate to be the same as that of unicast
733 Config::SetDefault ("ns3::WifiRemoteStationManager::NonUnicastMode",
734 StringValue (phyMode));
735
736 // install YansWifiPhy
738 wifi.SetStandard (WIFI_STANDARD_80211b);
739
740 YansWifiPhyHelper wifiPhy;
741 /*
742 * This is one parameter that matters when using FixedRssLossModel, set it to
743 * zero; otherwise, gain will be added.
744 */
745 wifiPhy.Set ("RxGain", DoubleValue (0));
746 // ns-3 supports RadioTap and Prism tracing extensions for 802.11b
747 wifiPhy.SetPcapDataLinkType (WifiPhyHelper::DLT_IEEE802_11_RADIO);
748
749 YansWifiChannelHelper wifiChannel;
750 wifiChannel.SetPropagationDelay ("ns3::ConstantSpeedPropagationDelayModel");
751 wifiPhy.SetChannel (wifiChannel.Create ());
752
753 // Add a MAC and disable rate control
754 WifiMacHelper wifiMac;
755 wifi.SetRemoteStationManager ("ns3::ConstantRateWifiManager",
756 "DataMode", StringValue (phyMode),
757 "ControlMode", StringValue (phyMode));
758 // Set it to ad-hoc mode
759 wifiMac.SetType ("ns3::AdhocWifiMac");
760 NetDeviceContainer devices = wifi.Install (wifiPhy, wifiMac, c);
761
762 // Create and install battery model and device models
763 // RV battery model
764 RvBatteryModelHelper rvModelHelper;
765 // Set alpha & beta values
766 rvModelHelper.Set ("RvBatteryModelAlphaValue", DoubleValue (m_alpha));
767 rvModelHelper.Set ("RvBatteryModelBetaValue", DoubleValue (m_beta));
768 rvModelHelper.Set ("RvBatteryModelLowBatteryThreshold", DoubleValue (0.0));
769 // install source
770 EnergySourceContainer sources = rvModelHelper.Install (c);
771 // device energy model
772 WifiRadioEnergyModelHelper radioEnergyHelper;
773 // set VariableLoadTestIDLE current, which will be the constant load
774 radioEnergyHelper.Set ("IdleCurrentA", DoubleValue (load));
775 // install on node
776 DeviceEnergyModelContainer deviceModels = radioEnergyHelper.Install (devices, sources);
777
778 // run simulation
779 Simulator::Stop (Seconds (70000.0));
780 Simulator::Run ();
781
782 Time actualLifetime;
783 Ptr<RvBatteryModel> srcPtr = DynamicCast<RvBatteryModel> (sources.Get (0));
784 actualLifetime = srcPtr->GetLifetime ();
785
786 NS_LOG_DEBUG ("Expected lifetime = " << expLifetime.As (Time::S));
787 NS_LOG_DEBUG ("Actual lifetime = " << actualLifetime.As (Time::S));
788
789 Simulator::Destroy ();
790
791 if (actualLifetime != expLifetime)
792 {
793 std::cerr << "ConstantLoadTest: Incorrect lifetime for load " << load << std::endl;
794 return true;
795 }
796
797 return false; // error free
798}
799
800bool
801BatteryLifetimeTest::VariableLoadTest (std::vector<double> loads,
802 std::vector<Time> timeStamps,
803 Time expLifetime)
804{
805 NS_ASSERT (loads.size () == timeStamps.size ());
806
807 // create single node
809 c.Create (1);
810
811 std::string phyMode ("DsssRate1Mbps");
812
813 // disable fragmentation for frames below 2200 bytes
814 Config::SetDefault ("ns3::WifiRemoteStationManager::FragmentationThreshold",
815 StringValue ("2200"));
816 // turn off RTS/CTS for frames below 2200 bytes
817 Config::SetDefault ("ns3::WifiRemoteStationManager::RtsCtsThreshold",
818 StringValue ("2200"));
819 // Fix non-unicast data rate to be the same as that of unicast
820 Config::SetDefault ("ns3::WifiRemoteStationManager::NonUnicastMode",
821 StringValue (phyMode));
822
823 // install YansWifiPhy
825 wifi.SetStandard (WIFI_STANDARD_80211b);
826
827 YansWifiPhyHelper wifiPhy;
828 /*
829 * This is one parameter that matters when using FixedRssLossModel, set it to
830 * zero; otherwise, gain will be added.
831 */
832 wifiPhy.Set ("RxGain", DoubleValue (0));
833 // ns-3 supports RadioTap and Prism tracing extensions for 802.11b
834 wifiPhy.SetPcapDataLinkType (WifiPhyHelper::DLT_IEEE802_11_RADIO);
835
836 YansWifiChannelHelper wifiChannel;
837 wifiChannel.SetPropagationDelay ("ns3::ConstantSpeedPropagationDelayModel");
838 wifiPhy.SetChannel (wifiChannel.Create ());
839
840 // Add a MAC and disable rate control
841 WifiMacHelper wifiMac;
842 wifi.SetRemoteStationManager ("ns3::ConstantRateWifiManager",
843 "DataMode", StringValue (phyMode),
844 "ControlMode", StringValue (phyMode));
845 // Set it to ad-hoc mode
846 wifiMac.SetType ("ns3::AdhocWifiMac");
847 NetDeviceContainer devices = wifi.Install (wifiPhy, wifiMac, c);
848
849 // Create and install battery model and device models
850 // RV battery model
851 RvBatteryModelHelper rvModelHelper;
852 // Set alpha & beta values
853 rvModelHelper.Set ("RvBatteryModelAlphaValue", DoubleValue (m_alpha));
854 rvModelHelper.Set ("RvBatteryModelBetaValue", DoubleValue (m_beta));
855 rvModelHelper.Set ("RvBatteryModelLowBatteryThreshold", DoubleValue (0.0));
856 // install source
857 EnergySourceContainer sources = rvModelHelper.Install (c);
858 // device energy model
859 WifiRadioEnergyModelHelper radioEnergyHelper;
860 // set VariableLoadTestIDLE current, which will be the constant load
861 radioEnergyHelper.Set ("IdleCurrentA", DoubleValue (loads[0]));
862 // install on node
863 DeviceEnergyModelContainer deviceModels = radioEnergyHelper.Install (devices, sources);
864
865
866 Ptr<WifiRadioEnergyModel> wifiDevicePtr = DynamicCast<WifiRadioEnergyModel> (deviceModels.Get (0));
867 // schedule load change events
868 for (uint32_t i = 1; i < loads.size (); i++)
869 {
870 Simulator::Schedule (timeStamps[i], &WifiRadioEnergyModel::SetIdleCurrentA,
871 wifiDevicePtr, loads[i]);
872 }
873
874 // run simulation
875 Simulator::Stop (Seconds (70000.0));
876 Simulator::Run ();
877
878 Time actualLifetime;
879 Ptr<RvBatteryModel> srcPtr = DynamicCast<RvBatteryModel> (sources.Get (0));
880 actualLifetime = srcPtr->GetLifetime ();
881
882 NS_LOG_DEBUG ("Expected lifetime = " << expLifetime.As (Time::S));
883 NS_LOG_DEBUG ("Actual lifetime = " << actualLifetime.As (Time::S));
884 NS_LOG_DEBUG ("Difference = " << (expLifetime - actualLifetime).As (Time::S));
885
886 Simulator::Destroy ();
887
888 // error tolerance = 120s
889 if (Abs (actualLifetime - expLifetime) > Seconds (120))
890 {
891 std::cerr << "VariableLoadTest: Incorrect lifetime." << std::endl;
892 return true;
893 }
894
895 return false; // error free
896}
897
This example was originally devised as a test, then it was converted to an example.
void CreateLoadProfiles(void)
Creates load profiles according to D.
bool ConstantLoadTest(double load, Time expLifetime)
double m_beta
Beta parameter of the battery model.
bool VariableLoadTest(std::vector< double > loads, std::vector< Time > timeStamps, Time expLifetime)
double m_alpha
Alpha parameter of the battery model.
std::vector< LoadProfile > m_loadProfiles
Load profiles.
Parse command-line arguments.
Definition: command-line.h:229
Holds a vector of ns3::DeviceEnergyModel pointers.
Ptr< DeviceEnergyModel > Get(uint32_t i) const
Get the i-th Ptr<DeviceEnergyModel> stored in this container.
DeviceEnergyModelContainer Install(Ptr< NetDevice > device, Ptr< EnergySource > source) const
This class can be used to hold variables of floating point type such as 'double' or 'float'.
Definition: double.h:41
Holds a vector of ns3::EnergySource pointers.
Ptr< EnergySource > Get(uint32_t i) const
Get the i-th Ptr<EnergySource> stored in this container.
EnergySourceContainer Install(Ptr< Node > node) const
holds a vector of ns3::NetDevice pointers
keep track of a set of node pointers.
void Create(uint32_t n)
Create n nodes and append pointers to them to the end of this NodeContainer.
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:74
Creates a RvBatteryModel object.
void Set(std::string name, const AttributeValue &v)
Hold variables of type string.
Definition: string.h:41
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:103
TimeWithUnit As(const enum Unit unit=Time::AUTO) const
Attach a unit to a Time, to facilitate output in a specific unit.
Definition: time.cc:432
helps to create WifiNetDevice objects
Definition: wifi-helper.h:323
create MAC layers for a ns3::WifiNetDevice.
void SetType(std::string type, Args &&... args)
void SetPcapDataLinkType(SupportedPcapDataLinkTypes dlt)
Set the data link type of PCAP traces to be used.
Definition: wifi-helper.cc:574
void Set(std::string name, const AttributeValue &v)
Definition: wifi-helper.cc:141
Assign WifiRadioEnergyModel to wifi devices.
void Set(std::string name, const AttributeValue &v) override
manage and create wifi channel objects for the YANS model.
void SetPropagationDelay(std::string name, std::string n0="", const AttributeValue &v0=EmptyAttributeValue(), std::string n1="", const AttributeValue &v1=EmptyAttributeValue(), std::string n2="", const AttributeValue &v2=EmptyAttributeValue(), std::string n3="", const AttributeValue &v3=EmptyAttributeValue(), std::string n4="", const AttributeValue &v4=EmptyAttributeValue(), std::string n5="", const AttributeValue &v5=EmptyAttributeValue(), std::string n6="", const AttributeValue &v6=EmptyAttributeValue(), std::string n7="", const AttributeValue &v7=EmptyAttributeValue())
Ptr< YansWifiChannel > Create(void) const
Make it easy to create and manage PHY objects for the YANS model.
void SetChannel(Ptr< YansWifiChannel > channel)
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file,...
Definition: assert.h:67
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:849
int64x64_t Abs(const int64x64_t &value)
Absolute value.
Definition: int64x64.h:205
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:205
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition: log.h:273
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1244
@ WIFI_STANDARD_80211b
devices
Definition: first.py:39
Every class exported by the ns3 library is enclosed in the ns3 namespace.
cmd
Definition: second.py:35
wifi
Definition: third.py:99
Load profile of the battery.
std::vector< Time > timeStamps
Timestamps container.
std::vector< double > loads
Loads container.
Time dualFoilLifeTime
Expected lifetime for a Dualfoil battery.
Time itsyLifetime
Expected lifetime for an ITSY battery.