This repository has been archived on 2020-04-08. You can view files and clone it, but cannot push or open issues or pull requests.
Files
Indoor/sensors/radio/WiFiGridNode.h
kazu 4f511d907e some fixes [multithreading,..]
needed interface changes [new options]
logger for android
wifi-ap-optimization
new test-cases
2016-09-28 12:19:14 +02:00

171 lines
4.2 KiB
C++

#ifndef WIFIGRIDNODE_H
#define WIFIGRIDNODE_H
#include <cstdint>
#include "AccessPoint.h"
#include "../../misc/Debug.h"
/**
* rssi model-estimation for one AP, denoted by its index [among all APs present within the map]
* the signal strength is stored as uint8_t and allows a granularity of 0.25 dB between -40 and -103 dB
*/
struct WiFiGridNodeAP {
private:
static const uint8_t UNUSED_IDX = 255;
private:
/** access-point index -> max 255 APs/Map */
uint8_t idx;
/** access-point rssi */
uint8_t rssi;
public:
/** empty ctor */
WiFiGridNodeAP() : idx(UNUSED_IDX), rssi(0) {
int i = 0; (void) i;
}
/** ctor */
WiFiGridNodeAP(const int idx, const float rssi) : idx(idx), rssi(stretch(rssi)) {
int i = 0; (void) i;
}
/** is this entry valid/used? */
bool isValid() const {return idx != UNUSED_IDX;}
/** set AP and its signal strength */
void set(const int apIdx, const float rssi) {
this->idx = apIdx;
this->rssi = stretch(rssi);
}
/** get the predicted signal-strength */
float getRSSI() const {return unstretch(rssi);}
/** get the access-point's index */
int getAPIdx() const {return idx;}
private:
/** [-40:-103] -> [0:252] => this allows 0.25 steps */
static inline int8_t stretch(float rssi) {
if (rssi > -40) {rssi = -40;}
if (rssi < -103) {rssi = -103;}
return std::round((-rssi - 40) * 4);
}
/** [0:252] -> [-40:-103] */
static inline float unstretch(const float rssi) {
return -(rssi / 4.0f + 40.0f);
}
};// __attribute__((packed));
/**
* base-class for grid-nodes that contain wifi signal-strength estimations.
* such estimations are calculated offline and added to each node.
* this also allows for using very complex signal-strength estimation models
*/
template <int maxAccessPoints> struct WiFiGridNode {
/** contains the 10 strongest APs measureable at this position */
WiFiGridNodeAP strongestAPs[maxAccessPoints];
/** ctor */
explicit WiFiGridNode() : strongestAPs() {
;
}
/** get the maximum number of APs each node is able to store */
int getMaxAPs() const {return maxAccessPoints;}
/**
* get the RSSI for the given AP
* returns 0 if unknown
*/
float getRSSI(const std::string& mac) const {
return getRSSI(MACAddress(mac));
}
/**
* get the RSSI for the given AP
* returns 0 if unknown
*/
float getRSSI(const MACAddress mac) const {
for (const WiFiGridNodeAP& ap : strongestAPs) {
//std::cout << getMapAPs()[ap.getAPIdx()].getMAC().asString() << std::endl;
//std::cout << mac.asString() << std::endl;
if (!ap.isValid()) {break;} // reached the end of all APs visible on this node
if (getMapAPs()[ap.getAPIdx()].getMAC() == mac) {return ap.getRSSI();} // does this APs MAC match with the requested MAC? -> found!
}
return 0;
}
/** get the number of access-points visible at this node */
int getNumVisibleAPs() const {
for (int i = 0; i < getMaxAPs(); ++i) {
if (!strongestAPs[i].isValid()) {return i;}
}
return getMaxAPs();
}
/** shared vector of all accesspoints the are present within the map. the IDX referes to this vector */
static std::vector<AccessPoint>& getMapAPs() {
static std::vector<AccessPoint> list;
return list;
}
protected:
static constexpr const char* name = "WiFiGridNode";
/** serialize static members */
static void staticSerialize(std::ostream& out) {
// number of APs within map
const int numAPs = getMapAPs().size();
// serialize number and APs within map
out.write((const char*) &numAPs, sizeof(numAPs));
out.write((const char*) getMapAPs().data(), sizeof(getMapAPs()[0])*numAPs);
Log::add(name, "serialized " + std::to_string(numAPs) + " APs");
}
/** deserialize static members */
static void staticDeserialize(std::istream& inp) {
// get number of APs within map
int numAPs;
inp.read((char*) &numAPs, sizeof(numAPs));
// allocate
getMapAPs().resize(numAPs);
// deserialize APs within map
inp.read((char*) getMapAPs().data(), sizeof(getMapAPs()[0])*numAPs);
Log::add(name, "de-serialized " + std::to_string(numAPs) + " APs");
std::string aps; for (const AccessPoint& ap : getMapAPs()) {aps += ap.getMAC().asString() + " ";}
Log::add(name, aps);
}
};// __attribute__((packed));
#endif // WIFIGRIDNODE_H