Browse Source

przebijanie NAT working 100%

master
Piotr Dergun 7 years ago
parent
commit
914b34070e
12 changed files with 350 additions and 10 deletions
  1. +17
    -0
      Log.cpp
  2. +2
    -0
      Log.h
  3. +1
    -1
      Makefile
  4. +14
    -2
      NATRouter.cpp
  5. +21
    -3
      Node.cpp
  6. +3
    -1
      Node.h
  7. +79
    -0
      P2PServer.cpp
  8. +26
    -0
      P2PServer.h
  9. +137
    -0
      Peer.cpp
  10. +37
    -0
      Peer.h
  11. +12
    -2
      Simulation.cpp
  12. +1
    -1
      common.h

+ 17
- 0
Log.cpp View File

@ -13,6 +13,8 @@ Log::Log()
this->delimiter = ""; this->delimiter = "";
this->lineNumber = 0; this->lineNumber = 0;
this->objectName = NULL; this->objectName = NULL;
this->writeMutex = Log::getMutex();
} }
LOG_COLOR Log::getColor() const LOG_COLOR Log::getColor() const
@ -61,6 +63,7 @@ void Log::print(string msg)
if (this->getObjectName() == NULL) if (this->getObjectName() == NULL)
return; return;
pthread_mutex_lock(this->writeMutex);
move(this->getLineNumber(), 0); move(this->getLineNumber(), 0);
clrtoeol(); clrtoeol();
@ -73,6 +76,8 @@ void Log::print(string msg)
attroff(COLOR_PAIR(this->getColor())); attroff(COLOR_PAIR(this->getColor()));
move(0, 0); move(0, 0);
pthread_mutex_unlock(this->writeMutex);
#else #else
cout << this->getObjectName()->c_str() << ": " << this->getDelimiter() << msg << endl; cout << this->getObjectName()->c_str() << ": " << this->getDelimiter() << msg << endl;
#endif #endif
@ -84,3 +89,15 @@ void Log::setLogParams(int lineNumber, LOG_COLOR color, string delimiter)
this->setColor(color); this->setColor(color);
this->setDelimiter(delimiter); this->setDelimiter(delimiter);
} }
pthread_mutex_t* Log::getMutex()
{
static pthread_mutex_t m;
static int mutex_initalized;
if (mutex_initalized != 0)
{
pthread_mutex_init(&m, NULL);
}
return &m;
}

+ 2
- 0
Log.h View File

@ -27,6 +27,7 @@ class Log
LOG_COLOR color; LOG_COLOR color;
string delimiter; string delimiter;
string *objectName; string *objectName;
pthread_mutex_t *writeMutex;
protected: protected:
string* getObjectName() const; string* getObjectName() const;
void setObjectName(string* objectName); void setObjectName(string* objectName);
@ -41,6 +42,7 @@ public:
int getLineNumber() const; int getLineNumber() const;
void setLineNumber(int lineNumber); void setLineNumber(int lineNumber);
void setLogParams(int lineNumber, LOG_COLOR color, string delimiter); void setLogParams(int lineNumber, LOG_COLOR color, string delimiter);
static pthread_mutex_t * getMutex();
}; };
#endif /* LOG_H_ */ #endif /* LOG_H_ */

+ 1
- 1
Makefile View File

@ -1,7 +1,7 @@
CXX = g++ CXX = g++
CXXFLAGS = -Wall -std=c++11 CXXFLAGS = -Wall -std=c++11
LDFLAGS = -pthread -lncurses LDFLAGS = -pthread -lncurses
OBJ = Log.o Packet.o Node.o NATItem.o NATRouter.o Peer.o Simulation.o
OBJ = Log.o Packet.o Node.o NATItem.o NATRouter.o Peer.o P2PServer.o Simulation.o
all: all:
+@make simulation +@make simulation

+ 14
- 2
NATRouter.cpp View File

@ -62,6 +62,10 @@ void NATRouter::onRecv()
Packet p = this->recv(); Packet p = this->recv();
stringstream s; stringstream s;
/*if (this->getHostname() == "Router 2") {
s << "src: " << p.getSrcIp() << ":" << p.getSrcPort() << "dst: " << p.getDstIp() << ":" << p.getDstPort();
this->print(s.str());
}*/
if (p.getSrcPort() != 0) if (p.getSrcPort() != 0)
{ {
// jezeli pakiet idzie z jednego wezla do drugiego w danej possieci to odeslij mu "jak switch" // jezeli pakiet idzie z jednego wezla do drugiego w danej possieci to odeslij mu "jak switch"
@ -87,7 +91,10 @@ void NATRouter::onRecv()
} }
else else
{ {
#ifndef DEBUG
this->print("onRecv() sleeping..."); this->print("onRecv() sleeping...");
#endif
} }
sleep(1); sleep(1);
@ -148,7 +155,7 @@ void NATRouter::sNAT(Packet *packet)
natItem = &this->natTable[port]; natItem = &this->natTable[port];
natItem->setIp(packet->getSrcIp()); natItem->setIp(packet->getSrcIp());
natItem->setPort(packet->getSrcPort()); natItem->setPort(packet->getSrcPort());
natItem->setTimeout(5);
natItem->setTimeout(/*5*/10);
stringstream ss; stringstream ss;
ss << "SNAT " << packet->getSrcIp() << ":" << packet->getSrcPort() << " --> " << this->getWanIp() << ":" << port; ss << "SNAT " << packet->getSrcIp() << ":" << packet->getSrcPort() << " --> " << this->getWanIp() << ":" << port;
@ -157,7 +164,7 @@ void NATRouter::sNAT(Packet *packet)
packet->setSrcPort(port); // zamieniam port lokalny na WAN'owy - z tablicy NAT packet->setSrcPort(port); // zamieniam port lokalny na WAN'owy - z tablicy NAT
this->print(ss.str()); this->print(ss.str());
sleep(1);
this->send(*packet, true); // wysylam dalej this->send(*packet, true); // wysylam dalej
natItem = NULL; natItem = NULL;
} }
@ -172,11 +179,16 @@ void NATRouter::dNAT(Packet* packet)
{ {
NATItem *natItem = &this->natTable[packet->getDstPort()]; NATItem *natItem = &this->natTable[packet->getDstPort()];
stringstream ss;
ss << "DNAT " << packet->getDstIp() << ":" << packet->getDstPort() << " --> " << natItem->getIp() << ":" << natItem->getPort();
packet->setDstIp(natItem->getIp()); // zamieniam IP lokalne na WAN'owe packet->setDstIp(natItem->getIp()); // zamieniam IP lokalne na WAN'owe
packet->setDstPort(natItem->getPort()); // zamieniam port NAT na lokalny wezla packet->setDstPort(natItem->getPort()); // zamieniam port NAT na lokalny wezla
//natItem->free(); // zwalniam port w routerze //natItem->free(); // zwalniam port w routerze
natItem->increaseTimeout(5); // podbijam o kolejne 5 sekund skoro transmisja trwa natItem->increaseTimeout(5); // podbijam o kolejne 5 sekund skoro transmisja trwa
this->print(ss.str());
sleep(1);
this->send(*packet, true); // wysylam dalej this->send(*packet, true); // wysylam dalej
natItem = NULL; natItem = NULL;

+ 21
- 3
Node.cpp View File

@ -152,7 +152,7 @@ bool Node::connectNode(Node *node, bool isExternal, bool firstConnected)
* funkcja wysyla, czyli przekazuje kopie pakietu kolejnemu wezlowi - docelowemu lub bramie domyslnej * funkcja wysyla, czyli przekazuje kopie pakietu kolejnemu wezlowi - docelowemu lub bramie domyslnej
* o ile jest skonfigurowana i istnieje do niej sciezka * o ile jest skonfigurowana i istnieje do niej sciezka
*/ */
bool Node::send(Packet packet, bool isRouter)
int Node::send(Packet packet, bool isRouter)
{ {
Node *node; Node *node;
node = this->findConnection(packet.getDstIp()); // znajdz bezposrednia trase node = this->findConnection(packet.getDstIp()); // znajdz bezposrednia trase
@ -172,13 +172,13 @@ bool Node::send(Packet packet, bool isRouter)
if (packet.getSrcPort() == 0) if (packet.getSrcPort() == 0)
{ {
// ustaw port zrodlowy na port losowy z zakresu [32768,61000] - zob. empheral port (port emferyczny) // ustaw port zrodlowy na port losowy z zakresu [32768,61000] - zob. empheral port (port emferyczny)
srand(time(NULL));
packet.setSrcPort(rand() % 32768 + 28233); packet.setSrcPort(rand() % 32768 + 28233);
} }
} }
node->putPacket(packet); node->putPacket(packet);
return true;
return packet.getSrcPort();
} }
/* /*
@ -264,3 +264,21 @@ string Node::getNetwork()
{ {
return this->netConf.network; return this->netConf.network;
} }
void Node::split(const std::string &s, char delim, vector<string> &elems)
{
stringstream ss;
ss.str(s);
string item;
while (getline(ss, item, delim))
{
elems.push_back(item);
}
}
vector<string> Node::split(const string &s, char delim)
{
vector<std::string> elems;
split(s, delim, elems);
return elems;
}

+ 3
- 1
Node.h View File

@ -33,6 +33,8 @@ protected:
string ipToString(unsigned int ip); string ipToString(unsigned int ip);
unsigned int stringToIp(string ip); unsigned int stringToIp(string ip);
string calculateNetwork(string ip, string mask); string calculateNetwork(string ip, string mask);
void split(const string &s, char delim, vector<string> &elems);
vector<string> split(const string &s, char delim);
public: public:
Node(); Node();
@ -42,7 +44,7 @@ public:
virtual ~Node(); virtual ~Node();
bool connectNode(Node *node, bool isExternal = false, bool firstConnected = false); bool connectNode(Node *node, bool isExternal = false, bool firstConnected = false);
bool send(Packet packet, bool isRouter = false);
int send(Packet packet, bool isRouter = false);
void putPacket(Packet packet); void putPacket(Packet packet);
// settery // settery

+ 79
- 0
P2PServer.cpp View File

@ -0,0 +1,79 @@
/*
* P2PServer.cpp
*
* Created on: 17.01.2017
* Author: Piotr Dergun
*/
#include "P2PServer.h"
P2PServer::P2PServer()
{
this->seedIp = "";
this->peerIp = "";
this->seedPort = 0;
this->peerPort = 0;
}
P2PServer::P2PServer(string hostname, string ip, string mask) : Node(hostname, ip, mask)
{
this->seedIp = "";
this->peerIp = "";
this->seedPort = 0;
this->peerPort = 0;
}
P2PServer::~P2PServer()
{
}
void P2PServer::onRecv()
{
stringstream ss;
while (true)
{
ss.str("");
Packet p = this->recv();
if (p.getSrcPort() != 0)
{
ss << "onRecv() Received \"" << p.getMsg() << "\" from " << p.getSrcIp() << ":" << p.getSrcPort();
this->print(ss.str());
sleep(1);
if (p.getMsg() == "getRemoteIPPort")
{
this->seedIp = p.getSrcIp();
this->seedPort = p.getSrcPort();
}
else if (p.getMsg() == "helloDownload")
{
this->peerIp = p.getSrcIp();
this->peerPort = p.getSrcPort();
}
if (this->seedPort != 0 && this->peerPort != 0)
{
ss.str("");
ss << "peerConnectionInfo:" << this->peerIp << ":" << this->peerPort;
Packet pp(ss.str());
pp.setDstIp(this->seedIp);
pp.setDstPort(this->seedPort);
pp.setSrcPort(p.getDstPort());
ss.str("");
ss << "Sending \"" << pp.getMsg() << "\" to " << pp.getDstIp() << ":" << pp.getDstPort();
this->print(ss.str());
this->send(pp);
sleep(1);
}
}
else
{
#ifndef DEBUG
this->print("onRecv() sleeping...");
#endif
sleep(1);
}
}
}

+ 26
- 0
P2PServer.h View File

@ -0,0 +1,26 @@
/*
* P2PServer.h
*
* Created on: 17.01.2017
* Author: Piotr Dergun
*/
#ifndef P2PSERVER_H_
#define P2PSERVER_H_
#include "common.h"
#include "Node.h"
class P2PServer : public Node
{
string seedIp, peerIp;
int seedPort, peerPort;
public:
P2PServer();
P2PServer(string hostname, string ip, string mask);
virtual ~P2PServer();
virtual void onRecv();
};
#endif /* P2PSERVER_H_ */

+ 137
- 0
Peer.cpp View File

@ -0,0 +1,137 @@
/*
* Peer.cpp
*
* Created on: 17.01.2017
* Author: piotrek
*/
#include "Peer.h"
Peer::Peer()
{
this->partId = 1;
this->srcPort = 0;
this->remotePort = 0;
this->sender = false;
}
Peer::Peer(string hostname, string ip, string mask, string gatewayIp) : Node(hostname, ip, mask, gatewayIp)
{
this->partId = 1;
this->srcPort = 0;
this->remotePort = 0;
this->sender = false;
}
void Peer::onRecv()
{
stringstream ss;
while (true)
{
ss.str("");
Packet p = this->recv();
if (p.getSrcPort() != 0)
{
// jezeli informacje o drugiej stronie
if (this->isSender() && this->remotePort == 0)
{
vector<string> x = split(p.getMsg(), ':');
this->remoteIp = x[1];
this->remotePort = atoi(x[2].c_str());
ss << "onRecv() REMOTE peer is " << this->remoteIp << ":" << this->remotePort;
this->print(ss.str());
sleep(1);
this->sendData();
}
else if (!this->isSender() && p.getMsg().find("data") != string::npos)
{
ss << "onRecv() Received \"" << p.getMsg() << "\" from " << p.getSrcIp() << ":" << p.getSrcPort();
this->print(ss.str());
sleep(1);
this->sendAck(p.getSrcIp(), p.getSrcPort());
}
else if (this->isSender() && p.getMsg().find("Ack") != string::npos)
{
ss << "onRecv() Received \"" << p.getMsg() << "\" from " << p.getSrcIp() << ":" << p.getSrcPort();
this->print(ss.str());
sleep(1);
this->sendData();
}
}
else
{
#ifndef DEBUG
this->print("onRecv() sleeping...");
#endif
}
sleep(1);
}
}
void Peer::connectToServer(string serverIp, int serverPort)
{
stringstream ss;
ss << "Connecting to " << serverIp << ":" << serverPort;
Packet p;
if (this->isSender())
p.setMsg("getRemoteIPPort");
else
p.setMsg("helloDownload");
p.setDstIp(serverIp);
p.setDstPort(serverPort);
this->srcPort = this->send(p);
ss << "\t RESULT: " << this->srcPort;
this->print(ss.str());
}
void Peer::sendData()
{
stringstream ss;
Packet p;
ss << "data-Part" << this->partId++;
p.setDstIp(this->remoteIp);
p.setDstPort(this->remotePort);
p.setSrcPort(this->srcPort);
p.setMsg(ss.str());
ss.str("");
ss << "Sending \"" << p.getMsg() << "\" to " << p.getDstIp() << ":" << p.getDstPort();
this->print(ss.str());
this->send(p);
}
bool Peer::isSender() const
{
return sender;
}
void Peer::setSender(bool sender)
{
this->sender = sender;
}
void Peer::sendAck(string dstIp, int dstPort)
{
stringstream ss;
Packet p;
ss << "data-Ack" << this->partId++;
p.setDstIp(dstIp);
p.setDstPort(dstPort);
p.setSrcPort(this->srcPort);
p.setMsg(ss.str());
ss.str("");
ss << "Sending \"" << p.getMsg() << "\" to " << p.getDstIp() << ":" << p.getDstPort();
this->print(ss.str());
this->send(p);
}

+ 37
- 0
Peer.h View File

@ -0,0 +1,37 @@
/*
* Peer.h
*
* Created on: 17.01.2017
* Author: piotrek
*/
#ifndef PEER_H_
#define PEER_H_
#include "common.h"
#include "Node.h"
class Peer : public Node
{
bool sender;
int srcPort;
string remoteIp;
int remotePort;
int partId;
public:
Peer();
Peer(string hostname, string ip, string mask, string gatewayIp);
virtual ~Peer() {};
virtual void onRecv();
void connectToServer(string serverIp, int serverPort);
bool isSender() const;
void setSender(bool sender);
protected:
void sendData();
void sendAck(string dstIp, int dstPort);
};
#endif /* PEER_H_ */

+ 12
- 2
Simulation.cpp View File

@ -9,9 +9,12 @@
#include "Node.h" #include "Node.h"
#include "NATRouter.h" #include "NATRouter.h"
#include "Peer.h" #include "Peer.h"
#include "P2PServer.h"
Simulation::Simulation() Simulation::Simulation()
{ {
srand(time(NULL));
this->rows = 0; this->rows = 0;
this->cols = 0; this->cols = 0;
#ifndef DEBUG #ifndef DEBUG
@ -145,11 +148,14 @@ void Simulation::resizeWnd()
void Simulation::timer() void Simulation::timer()
{ {
#ifndef DEBUG
char str[10]; char str[10];
int h,m, s; int h,m, s;
unsigned long timeElapsed; unsigned long timeElapsed;
#endif
while(true) while(true)
{ {
#ifndef DEBUG
refresh(); refresh();
timeElapsed = time(NULL) - this->startTime; timeElapsed = time(NULL) - this->startTime;
h = timeElapsed / 3600; h = timeElapsed / 3600;
@ -159,6 +165,7 @@ void Simulation::timer()
sprintf(str, "%02d:%02d:%02d", h, m, s); sprintf(str, "%02d:%02d:%02d", h, m, s);
move(0, this->cols-strlen(str)); move(0, this->cols-strlen(str));
printw(str); printw(str);
#endif
usleep(100000); // 100 ms usleep(100000); // 100 ms
//sleep(1); //sleep(1);
} }
@ -168,6 +175,7 @@ void Simulation::p2pSimulation()
{ {
this->print("Creating P2P peers"); this->print("Creating P2P peers");
Peer peer1("Peer 1", "192.168.1.2", "255.255.255.0", "192.168.1.1"); Peer peer1("Peer 1", "192.168.1.2", "255.255.255.0", "192.168.1.1");
peer1.setSender(true);
peer1.setLogParams(0, GREEN, "\t\t"); peer1.setLogParams(0, GREEN, "\t\t");
Peer peer2("Peer 2", "10.0.0.2", "255.255.255.0", "10.0.0.1"); Peer peer2("Peer 2", "10.0.0.2", "255.255.255.0", "10.0.0.1");
peer2.setLogParams(4, CYAN, "\t\t"); peer2.setLogParams(4, CYAN, "\t\t");
@ -194,7 +202,7 @@ void Simulation::p2pSimulation()
sleep(1); sleep(1);
this->print("Creating P2P server"); this->print("Creating P2P server");
Node server("Server", "80.80.90.91", "255.255.255.255");
P2PServer server("Server", "80.80.90.91", "255.255.255.255");
server.setLogParams(2, YELLOW, "\t\t"); server.setLogParams(2, YELLOW, "\t\t");
server.print("IP 80.80.90.91/32"); server.print("IP 80.80.90.91/32");
sleep(1); sleep(1);
@ -221,11 +229,13 @@ void Simulation::p2pSimulation()
this->createThread("r1", NODE_RECV, &r1); this->createThread("r1", NODE_RECV, &r1);
this->createThread("r2", NODE_RECV, &r2); this->createThread("r2", NODE_RECV, &r2);
this->createThread("s1", NODE_RECV, &server); this->createThread("s1", NODE_RECV, &server);
this->createThread("p2", NODE_RECV, &peer2);
peer1.connectToServer("80.80.90.91", 6565); peer1.connectToServer("80.80.90.91", 6565);
peer2.connectToServer("80.80.90.91", 6565);
sleep(1); sleep(1);
this->createThread("p1", NODE_RECV, &peer1); this->createThread("p1", NODE_RECV, &peer1);
this->createThread("p2", NODE_RECV, &peer2);
while(1); while(1);

+ 1
- 1
common.h View File

@ -2,7 +2,7 @@
* common.h * common.h
* *
* Created on: 10.01.2017 * Created on: 10.01.2017
* Author: piotrek
* Author: Piotr Dergun
*/ */
#ifndef COMMON_H_ #ifndef COMMON_H_

Loading…
Cancel
Save