-
Notifications
You must be signed in to change notification settings - Fork 4
/
Copy pathCustomAppLayer.cc
executable file
·271 lines (217 loc) · 8 KB
/
CustomAppLayer.cc
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU Lesser General Public License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this program. If not, see http://www.gnu.org/licenses/.
//
#include "CustomAppLayer.h"
using namespace std;
CustomAppLayer::CustomAppLayer()
{
// 1. General variables
packageID = 0; // Package ID
numSent = 0; // Sent packages
numReceived = 0; // Received packages
totalDistance = 0; // Total distance
lastAccelerationPlatoon = 0; // Last acceleration calculated with CACC
localLeaderAcceleration = 0; // Acceleration of leader
localLeaderSpeed = 0; // // Speed of leader
//2 . Platoon's parameters (CACC)
alpha1 = 0.5;
alpha2 = 0.5;
alpha3 = 0.3;
alpha4 = 0.1;
alpha5 = 0.04;
alphaLag = 0.8;
length_vehicle_front = 2;
desiredSpacing = 2;
beaconInterval = 0.1;
platoonInterval = 1;
beaconingEnabled = false;
}
double CustomAppLayer::getAccelerationPlatoon()
{
// 1. PREPARE
//List without duplicates
std::vector<NodeInfo*> noDuplicateInfo;
double distanceBetweenActualAndFront;
//Add NodeInfo objects to the list without duplicates
for (int i = 0; i < int(nodeInfoVector.size()); i++)
{
NodeInfo* nodeInfo = nodeInfoVector.back();
bool existeInfo = false;
//Iterate the list without duplicates
for (std::vector<NodeInfo*>::iterator it = noDuplicateInfo.begin(); it != noDuplicateInfo.end();
++it)
{
NodeInfo* n = *it;
//If exist a package from the same source node, it won't be added to the list without duplicates
if (n->getSrcAddress() == nodeInfo->getSrcAddress())
{
existeInfo = true;
break;
}
}
//If a package from the same source wasn't found, it will be added to the list without duplicates
if (existeInfo == false)
{
noDuplicateInfo.push_back(nodeInfo);
}
//Delete the package from NodeInfoVector
nodeInfoVector.pop_back();
}
// 2. START PLATOON
//Calculate distance between nodes and current to determine the nearest to the current
NodeInfo* nearestNode = NULL;
NodeInfo* leaderNode = NULL;
cout << "Node[" << getMyAddress() << "]: Running Platoon Update" << endl;
if (noDuplicateInfo.size() > 0)
{
//a. Determine the nearest and the leader nodes
for (std::vector<NodeInfo*>::iterator it = noDuplicateInfo.begin(); it != noDuplicateInfo.end();
++it)
{
NodeInfo* nodeInfo = *it;
//Get distance to current from sending node
int addr_node = nodeInfo->getSrcAddress();
double distanceToActual = nodeInfo->getDistanceToCurrent();
//Asign leader
if (addr_node == 0)
{
leaderNode = *it;
}
//If don't exist a nearest node and the distance between the node and the current is more than zero, this is the current nearest node
if (distanceToActual > 0 && nearestNode == NULL)
{
nearestNode = *it;
}
//If there is a nearest node, we have to compare the current node and the current nearest node
if (nearestNode != NULL)
{
//Compare with the current nearest node
double distanceToActual_nearest = nearestNode->getDistanceToCurrent();
//If distance is below than the current nearest distance, it will be the nearest node
if (distanceToActual > 0 && distanceToActual < distanceToActual_nearest)
{
nearestNode = *it;
}
}
}
//b. Get information from the nearest node in the front
double rel_speed_front;
double spacing_error;
double nodeFrontAcceleration;
if (nearestNode != NULL)
{
//Calculate relative speed to the node in front
rel_speed_front = getMySpeed() - nearestNode->getSpeed();
//Calculate spacing error
distanceBetweenActualAndFront = nearestNode->getDistanceToCurrent();
spacing_error = -distanceBetweenActualAndFront + length_vehicle_front + desiredSpacing;
nodeFrontAcceleration = nearestNode->getAcceleration();
}
else
{
rel_speed_front = 0;
spacing_error = 0;
nodeFrontAcceleration = 0;
}
//c. Get information from leader
double leaderAcceleration;
double leaderSpeed;
if (leaderNode == NULL)
{
//We use the data coming with beaconing
if (nearestNode != NULL && beaconingEnabled == true)
{
leaderAcceleration = nearestNode->getLeaderAcceleration();
leaderSpeed = nearestNode->getLeaderSpeed();
localLeaderAcceleration = nearestNode->getLeaderAcceleration();
localLeaderSpeed = nearestNode->getLeaderSpeed();
}
else
{
leaderAcceleration = 0;
leaderSpeed = 0;
localLeaderAcceleration = 0;
localLeaderSpeed = 0;
}
}
else
{
leaderAcceleration = leaderNode->getAcceleration();
leaderSpeed = leaderNode->getSpeed();
}
//Print data for calculation
cout << "Node[" << getMyAddress() << "]: Platoon parameters" << endl;
cout << "Distance to Vehicle in Front=" << distanceBetweenActualAndFront << endl;
cout << "Vehicle in Front Acceleration=" << nodeFrontAcceleration << endl;
cout << "Leader Acceleration=" << leaderAcceleration << endl;
cout << "Relative speed vehicule in front=" << rel_speed_front << endl;
cout << "Leader speed=" << leaderSpeed << endl;
cout << "My speed=" << getMySpeed() << endl;
cout << "Spacing Error=" << spacing_error << endl;
//d. Calculate (Acceleration desired) A_des
double A_des = alpha1 * nodeFrontAcceleration + alpha2 * leaderAcceleration
- alpha3 * rel_speed_front - alpha4 * (getMySpeed() - leaderSpeed)
- alpha5 * spacing_error;
//e. Calculate desired acceleration adding a delay
double A_des_lag = (alphaLag * A_des) + ((1 - alphaLag) * lastAccelerationPlatoon);
lastAccelerationPlatoon = A_des_lag;
return A_des_lag;
}
else
{
return 0;
}
}
/**
* Handle messages coming from outside
*/
void CustomAppLayer::handleLowerMsg(NodeInfo* nodeInfo)
{
numReceived++;
//Get information from package to forward to other nodes
double speed = nodeInfo->getSpeed();
double acceleration = nodeInfo->getAcceleration();
int address = nodeInfo->getSrcAddress();
cout << "Info from: " << address << endl;
//Save leader acceleration and speed
if (address == 0)
{
localLeaderAcceleration = acceleration;
localLeaderSpeed = speed;
}
else if (beaconingEnabled == true)
{
//Package coming with beaconing
}
//Save package in NodeInfoVector
nodeInfoVector.push_back(nodeInfo);
return;
}
//Getters and setters
void CustomAppLayer::setMyAddress(double newAddress)
{
myAddress = newAddress;
}
double CustomAppLayer::getMyAddress()
{
return myAddress;
}
void CustomAppLayer::setMySpeed(double newSpeed)
{
mySpeed = newSpeed;
}
double CustomAppLayer::getMySpeed()
{
return mySpeed;
}