Commit 3434115d authored by Marc Schiller's avatar Marc Schiller
Browse files

Fixed calculation of overloading. Worked on documentation.

parent a362cb93
...@@ -521,8 +521,9 @@ public class FiveGTopologyView extends AbstractTopologyView<CellLink> { ...@@ -521,8 +521,9 @@ public class FiveGTopologyView extends AbstractTopologyView<CellLink> {
public long getBandwidth(boolean isBroadcast) { public long getBandwidth(boolean isBroadcast) {
assert (apLinkData != null && supportsAccessPoints) assert (apLinkData != null && supportsAccessPoints)
|| apLinkData == null; || apLinkData == null;
return apLinkData != null ? apLinkData.getBandwidth(isUpload) long tmp = apLinkData != null ? apLinkData.getBandwidth(isUpload)
: linkData.getBandwidth(isUpload); : linkData.getBandwidth(isUpload);
return tmp;
} }
@Override @Override
......
...@@ -48,8 +48,17 @@ public class ModelBasedSegmentDatabase ...@@ -48,8 +48,17 @@ public class ModelBasedSegmentDatabase
return new ModelBasedEntry(segmentID); return new ModelBasedEntry(segmentID);
} }
/**
* Add a model to Database
*
* @param model
* the model to add
*/
public void setModel(AbstractModel model) { public void setModel(AbstractModel model) {
// Enable debugging
model.debug(); model.debug();
// Check if model is valid
ParameterType type = model.getParameterType(); ParameterType type = model.getParameterType();
if (type == null) { if (type == null) {
throw new ConfigurationException( throw new ConfigurationException(
...@@ -64,11 +73,20 @@ public class ModelBasedSegmentDatabase ...@@ -64,11 +73,20 @@ public class ModelBasedSegmentDatabase
Integer segmentID = new Integer(model.getSegmentID()); Integer segmentID = new Integer(model.getSegmentID());
// Check if there is no contradicting model
if (models.containsKey(type)) { if (models.containsKey(type)) {
// There is already this Type // There is already this Type
if (models.get(type).containsKey(segmentID)) { if (models.get(type).containsKey(segmentID)) {
// There is already this SegID // There is already this SegID
if (models.get(type).get(segmentID).containsKey(dir) || (models.get(type).get(segmentID).containsKey(Direction.BOTH) && (dir.equals(Direction.DOWNLOAD) || dir.equals(Direction.UPLOAD)))|| (dir.equals(Direction.BOTH) && (models.get(type).get(segmentID).containsKey(Direction.DOWNLOAD) || models.get(type).get(segmentID).containsKey(Direction.UPLOAD)))) { if (models.get(type).get(segmentID).containsKey(dir)
|| (models.get(type).get(segmentID)
.containsKey(Direction.BOTH)
&& (dir.equals(Direction.DOWNLOAD)
|| dir.equals(Direction.UPLOAD)))
|| (dir.equals(Direction.BOTH) && (models.get(type)
.get(segmentID).containsKey(Direction.DOWNLOAD)
|| models.get(type).get(segmentID)
.containsKey(Direction.UPLOAD)))) {
// There is already a model defined // There is already a model defined
throw new ConfigurationException( throw new ConfigurationException(
"Conflicting Models for SegmentID " + segmentID "Conflicting Models for SegmentID " + segmentID
...@@ -99,10 +117,19 @@ public class ModelBasedSegmentDatabase ...@@ -99,10 +117,19 @@ public class ModelBasedSegmentDatabase
models.put(type, tmp2); models.put(type, tmp2);
} }
System.out.println(models.toString());
} }
/**
* Get the model for the specific combination
*
* @param segID
* The SegmentID to get the model for
* @param type
* The Type of the Parameter
* @param isUpload
* Is it a Up or Downlink
* @return The Model for the given segment
*/
AbstractModel getModel(int segID, ParameterType type, Boolean isUpload) { AbstractModel getModel(int segID, ParameterType type, Boolean isUpload) {
Integer segmentID = new Integer(segID); Integer segmentID = new Integer(segID);
...@@ -141,26 +168,38 @@ public class ModelBasedSegmentDatabase ...@@ -141,26 +168,38 @@ public class ModelBasedSegmentDatabase
} }
public class ModelBasedEntry implements FiveGTopologyDatabase.Entry { public class ModelBasedEntry implements FiveGTopologyDatabase.Entry {
// How is a overload defined
private final long OVERLOAD_LATENCY = 9999 * Time.MILLISECOND; private final long OVERLOAD_LATENCY = 9999 * Time.MILLISECOND;
private final long OVERLOAD_BANDWIDTH = (long) 0.1; private final long OVERLOAD_BANDWIDTH = (long) 0.1;
private final double OVERLOAD_DROPRATE = 1; private final double OVERLOAD_DROPRATE = 1;
// When is a node considered overloaded
private final long THRESHOLD_LATENCY = Time.SECOND; private final long THRESHOLD_LATENCY = Time.SECOND;
private final long THRESHOLD_BANDWIDTH = 10; private final long THRESHOLD_BANDWIDTH = 10;
private final double THRESHOLD_DROPRATE = 1; private final double THRESHOLD_DROPRATE = 1;
private HashMap<ParameterType, HashMap<Direction, Long>> currentValues = new HashMap<>();
// Other storage
private final int segment; private final int segment;
private boolean isAvailable = true; private boolean isAvailable = true;
private HashSet<MacAddress> hostsInSegment = new HashSet<>(); private HashSet<MacAddress> hostsInSegment = new HashSet<>();
private boolean overload;
// The current metrics of this segment
private long bandUp;
private long bandDown;
private long latUp;
private long latDown;
private double dropUp;
private double dropDown;
/**
* Create a new entry for the given segment
* @param segment
*/
public ModelBasedEntry(int segment) { public ModelBasedEntry(int segment) {
this.segment = segment; this.segment = segment;
evaluateAll(); calc();
} }
@Override @Override
...@@ -168,40 +207,66 @@ public class ModelBasedSegmentDatabase ...@@ -168,40 +207,66 @@ public class ModelBasedSegmentDatabase
return segment; return segment;
} }
/**
* A host leaves this segment
*/
public void onHostLeavesSegment(MacAddress hostAddr) { public void onHostLeavesSegment(MacAddress hostAddr) {
// Remove MAC from current users
this.hostsInSegment.remove(hostAddr); this.hostsInSegment.remove(hostAddr);
evaluateAll(); calc();
} }
/**
* A host enters this segment
*/
public void onHostEntersSegment(MacAddress hostAddr) { public void onHostEntersSegment(MacAddress hostAddr) {
// Add MAC to current users
this.hostsInSegment.add(hostAddr); this.hostsInSegment.add(hostAddr);
evaluateAll(); calc();
} }
@Override @Override
public double getDropProbability(boolean isUpload) { public double getDropProbability(boolean isUpload) {
if(isUpload) { // Segment is overloaded or not available return overloaded drop probability
return this.currentValues.get(ParameterType.DROPRATE).get(Direction.UPLOAD); if (!isAvailable || overload) {
return OVERLOAD_DROPRATE;
}
// Return calculated drop probability
if (isUpload) {
return dropUp;
} else { } else {
return this.currentValues.get(ParameterType.DROPRATE).get(Direction.DOWNLOAD); return dropDown;
} }
} }
@Override @Override
public long getLatency(boolean isUpload) { public long getLatency(boolean isUpload) {
if(isUpload) { // Segment is overloaded or not available return overloaded latency
return this.currentValues.get(ParameterType.LATENCY).get(Direction.UPLOAD); if (!isAvailable || overload) {
return OVERLOAD_LATENCY;
}
// Return calculated latency
if (isUpload) {
return latUp;
} else { } else {
return this.currentValues.get(ParameterType.LATENCY).get(Direction.DOWNLOAD); return latDown;
} }
} }
@Override @Override
public long getBandwidth(boolean isUpload) { public long getBandwidth(boolean isUpload) {
if(isUpload) { // Segment is overloaded or not available return overloaded bandwidth
return this.currentValues.get(ParameterType.BANDWIDTH).get(Direction.UPLOAD); if (!isAvailable || overload) {
return OVERLOAD_BANDWIDTH;
}
// Return calculated bandwidth
if (isUpload) {
return bandUp;
} else { } else {
return this.currentValues.get(ParameterType.BANDWIDTH).get(Direction.DOWNLOAD); return bandDown;
} }
} }
...@@ -214,63 +279,50 @@ public class ModelBasedSegmentDatabase ...@@ -214,63 +279,50 @@ public class ModelBasedSegmentDatabase
public void setAvailability(boolean isAvailable) { public void setAvailability(boolean isAvailable) {
this.isAvailable = isAvailable; this.isAvailable = isAvailable;
} }
private void evaluateAll() { /**
int currentUsers = this.hostsInSegment.size(); * Recalculate every metric when a host leaves or enters
*/
private void calc() {
int users = this.hostsInSegment.size();
// Assume not overloaded
this.overload = false;
// Calc Bandwidth // Calc Bandwidth
long bandUp = getModel(getSegmentID(), ParameterType.BANDWIDTH, true).getLong(currentUsers); this.bandUp = getModel(getSegmentID(), ParameterType.BANDWIDTH,
long bandDown = getModel(getSegmentID(), ParameterType.BANDWIDTH, true).getLong(currentUsers); true).getLong(users);
this.bandDown = getModel(getSegmentID(), ParameterType.BANDWIDTH,
false).getLong(users);
if (bandDown <= THRESHOLD_BANDWIDTH
|| bandUp <= THRESHOLD_BANDWIDTH) {
overload = true;
System.out.println("Bandwidth is overloaded in Segment: " + getSegmentID());
}
// Calc Latency // Calc Latency
long latencyUp = getModel(getSegmentID(), ParameterType.LATENCY, true).getLong(currentUsers); this.latUp = getModel(getSegmentID(), ParameterType.LATENCY, true)
long latencyDown = getModel(getSegmentID(), ParameterType.LATENCY, true).getLong(currentUsers); .getLong(users);
this.latDown = getModel(getSegmentID(), ParameterType.LATENCY,
// Calc DropRate false).getLong(users);
double droprateUp = getModel(getSegmentID(), ParameterType.DROPRATE, true).getLong(currentUsers);
double droprateDown = getModel(getSegmentID(), ParameterType.DROPRATE, true).getLong(currentUsers); if (latUp >= THRESHOLD_LATENCY || latDown >= THRESHOLD_LATENCY) {
overload = true;
// One Value is above threshold -> everyone is down System.out.println("Latency is overloaded in Segment: " + getSegmentID());
if(!isAvailable || bandUp <= THRESHOLD_BANDWIDTH || bandDown <= THRESHOLD_BANDWIDTH || latencyUp >= THRESHOLD_LATENCY || latencyDown >= THRESHOLD_LATENCY || droprateDown >= THRESHOLD_DROPRATE || droprateUp >= THRESHOLD_DROPRATE) { }
//System.out.println("Overload!");
HashMap<Direction, Long> tmp = new HashMap<>(2); // Calc Droprate
tmp.put(Direction.DOWNLOAD, OVERLOAD_BANDWIDTH); this.dropUp = getModel(getSegmentID(), ParameterType.DROPRATE, true)
tmp.put(Direction.UPLOAD, OVERLOAD_BANDWIDTH); .getDouble(users);
this.dropDown = getModel(getSegmentID(), ParameterType.DROPRATE,
this.currentValues.put(ParameterType.BANDWIDTH, tmp); false).getDouble(users);
tmp = new HashMap<>(2); if (dropUp >= THRESHOLD_DROPRATE
tmp.put(Direction.DOWNLOAD, OVERLOAD_LATENCY); || dropDown >= THRESHOLD_DROPRATE) {
tmp.put(Direction.UPLOAD, OVERLOAD_LATENCY); overload = true;
System.out.println("Droprate is overloaded in Segment: " + getSegmentID());
this.currentValues.put(ParameterType.LATENCY, tmp);
tmp = new HashMap<>(2);
tmp.put(Direction.DOWNLOAD, (long) OVERLOAD_DROPRATE);
tmp.put(Direction.UPLOAD, (long) OVERLOAD_DROPRATE);
this.currentValues.put(ParameterType.DROPRATE, tmp);
} else {
//System.out.println("Everything ok!");
HashMap<Direction, Long> tmp = new HashMap<>(2);
tmp.put(Direction.DOWNLOAD, bandDown);
tmp.put(Direction.UPLOAD, bandUp);
this.currentValues.put(ParameterType.BANDWIDTH, tmp);
tmp = new HashMap<>(2);
tmp.put(Direction.DOWNLOAD, latencyDown);
tmp.put(Direction.UPLOAD, latencyUp);
this.currentValues.put(ParameterType.LATENCY, tmp);
tmp = new HashMap<>(2);
tmp.put(Direction.DOWNLOAD, (long) droprateDown);
tmp.put(Direction.UPLOAD, (long) droprateUp);
this.currentValues.put(ParameterType.DROPRATE, tmp);
} }
//System.out.println(this.currentValues);
} }
} }
} }
...@@ -26,12 +26,13 @@ import de.tud.kom.p2psim.impl.topology.views.fiveg.utils.Graph; ...@@ -26,12 +26,13 @@ import de.tud.kom.p2psim.impl.topology.views.fiveg.utils.Graph;
import de.tud.kom.p2psim.impl.topology.views.fiveg.utils.ParameterType; import de.tud.kom.p2psim.impl.topology.views.fiveg.utils.ParameterType;
public abstract class AbstractModel { public abstract class AbstractModel {
// Storage
private int segmentID = -1; private int segmentID = -1;
private ParameterType type; private ParameterType type;
private Direction dir = Direction.BOTH; private Direction dir = Direction.BOTH;
// Is debug enabled for this model
private boolean debug = false; private boolean debug = false;
public void setSegmentID(int segmentid) { public void setSegmentID(int segmentid) {
...@@ -43,8 +44,13 @@ public abstract class AbstractModel { ...@@ -43,8 +44,13 @@ public abstract class AbstractModel {
return this.segmentID; return this.segmentID;
} }
/**
* Set the parameter type {@link ParameterType}
* @param param
*/
public void setParameterType(String param) { public void setParameterType(String param) {
param = param.toUpperCase(); param = param.toUpperCase();
// Check if type is valid
try { try {
this.type = ParameterType.valueOf(param); this.type = ParameterType.valueOf(param);
} catch (IllegalArgumentException e) { } catch (IllegalArgumentException e) {
...@@ -63,6 +69,10 @@ public abstract class AbstractModel { ...@@ -63,6 +69,10 @@ public abstract class AbstractModel {
return type; return type;
} }
/**
* Set the direction of model {@link Direction}
* @param param
*/
public void setDirection(String param) { public void setDirection(String param) {
param = param.toUpperCase(); param = param.toUpperCase();
try { try {
...@@ -83,8 +93,12 @@ public abstract class AbstractModel { ...@@ -83,8 +93,12 @@ public abstract class AbstractModel {
return dir; return dir;
} }
/**
* Enable debugging
* @param debug
*/
public void setDebug(boolean debug) { public void setDebug(boolean debug) {
this.debug = true; this.debug = debug;
} }
public boolean getDebug() { public boolean getDebug() {
...@@ -95,8 +109,11 @@ public abstract class AbstractModel { ...@@ -95,8 +109,11 @@ public abstract class AbstractModel {
public abstract double getDouble(int users); public abstract double getDouble(int users);
/**
* Debug this model
*/
public void debug() { public void debug() {
Graph test = new Graph("Debug Graph"); Graph test = new Graph();
test.setModel(this); test.setModel(this);
} }
} }
/*
* Copyright (c) 2005-2010 KOM – Multimedia Communications Lab
*
* This file is part of PeerfactSim.KOM.
*
* PeerfactSim.KOM is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* any later version.
*
* PeerfactSim.KOM 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 General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with PeerfactSim.KOM. If not, see <http://www.gnu.org/licenses/>.
*
*/
package de.tud.kom.p2psim.impl.topology.views.fiveg.models;
/**
* A Constant Model which return always the constant value C
* c(u) = C
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public class ConstantModel extends AbstractModel {
private long c = 0;
public void setC(long c) {
this.c = c;
}
@Override
public long getLong(int users) {
return this.c;
}
@Override
public double getDouble(int users) {
return this.c;
}
public String toString() {
return "Constant Model: c(u) = " + c;
}
}
...@@ -19,7 +19,12 @@ ...@@ -19,7 +19,12 @@
*/ */
package de.tud.kom.p2psim.impl.topology.views.fiveg.models; package de.tud.kom.p2psim.impl.topology.views.fiveg.models;
/**
* A cut off model based on the heaviside step function.
* cut(u) = a * θ(c * u + d) + b
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public class CutOffModel extends AbstractModel { public class CutOffModel extends AbstractModel {
private long a = 1; private long a = 1;
......
...@@ -20,6 +20,12 @@ ...@@ -20,6 +20,12 @@
package de.tud.kom.p2psim.impl.topology.views.fiveg.models; package de.tud.kom.p2psim.impl.topology.views.fiveg.models;
/**
* An exponential model
* exp(u) = a * e^(c * u + d) + b
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public class ExponentialModel extends AbstractModel { public class ExponentialModel extends AbstractModel {
// exp(u) = a * e ^(c * u + d) + b // exp(u) = a * e ^(c * u + d) + b
......
...@@ -20,6 +20,12 @@ ...@@ -20,6 +20,12 @@
package de.tud.kom.p2psim.impl.topology.views.fiveg.models; package de.tud.kom.p2psim.impl.topology.views.fiveg.models;
/**
* Linear Model
* lin(u) = a * u + b
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public class LinearModel extends AbstractModel { public class LinearModel extends AbstractModel {
private long a = 0; private long a = 0;
...@@ -44,7 +50,7 @@ public class LinearModel extends AbstractModel { ...@@ -44,7 +50,7 @@ public class LinearModel extends AbstractModel {
} }
public String toString() { public String toString() {
return "Linear Model: f(u) = " + a + " * u + " + b; return "Linear Model: lin(u) = " + a + " * u + " + b;
} }
} }
...@@ -20,10 +20,14 @@ ...@@ -20,10 +20,14 @@
package de.tud.kom.p2psim.impl.topology.views.fiveg.models; package de.tud.kom.p2psim.impl.topology.views.fiveg.models;
/**
* Logarithmic model
* log(u) = a * ln(c * u + d) + b
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public class LogarithmicModel extends AbstractModel { public class LogarithmicModel extends AbstractModel {
// log(u) = a * ln(c * u + d) + b
private long a = 1; private long a = 1;
private long b = 0; private long b = 0;
......
...@@ -20,6 +20,11 @@ ...@@ -20,6 +20,11 @@
package de.tud.kom.p2psim.impl.topology.views.fiveg.utils; package de.tud.kom.p2psim.impl.topology.views.fiveg.utils;
/**
* Enumeration for defining the direction (Up,Down or Both) for a model.
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public enum Direction { public enum Direction {
BOTH(), BOTH(),
UPLOAD(), UPLOAD(),
......
...@@ -29,15 +29,22 @@ import org.jfree.ui.ApplicationFrame; ...@@ -29,15 +29,22 @@ import org.jfree.ui.ApplicationFrame;
import de.tud.kom.p2psim.impl.topology.views.fiveg.models.AbstractModel; import de.tud.kom.p2psim.impl.topology.views.fiveg.models.AbstractModel;
/**
* A simple graph for debugging the models
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public class Graph extends ApplicationFrame { public class Graph extends ApplicationFrame {
public Graph(String title) { public Graph() {
super(title); super("Debug Graph");
// TODO: Schließen ohne simonstrator zu killen.
} }
public void setModel(AbstractModel model) { public void setModel(AbstractModel model) {
if (model.getDebug()) { if (model.getDebug()) {
DefaultCategoryDataset dataset = new DefaultCategoryDataset(); DefaultCategoryDataset dataset = new DefaultCategoryDataset();
// TODO: Get max users.
for (int i = 0; i <= 500; i += 1) { for (int i = 0; i <= 500; i += 1) {
System.out.println(model.getDouble(i)); System.out.println(model.getDouble(i));
dataset.addValue(model.getDouble(i), "Value", dataset.addValue(model.getDouble(i), "Value",
......
...@@ -20,6 +20,11 @@ ...@@ -20,6 +20,11 @@
package de.tud.kom.p2psim.impl.topology.views.fiveg.utils; package de.tud.kom.p2psim.impl.topology.views.fiveg.utils;
/**
* Enumeration for defining the type (Bandwidth, Drop Rate, Latency) for a model.
* @author Marc Schiller
* @version 1.0, 15 Dec 2016
*/
public enum ParameterType { public enum ParameterType {
BANDWIDTH(), BANDWIDTH(),
DROPRATE(), DROPRATE(),
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment