]> git.sesse.net Git - greproxy/commitdiff
Move more stuff into the classes. Not fully orthogonal yet.
authorSteinar H. Gunderson <sgunderson@bigfoot.com>
Fri, 6 Feb 2015 23:57:52 +0000 (00:57 +0100)
committerSteinar H. Gunderson <sgunderson@bigfoot.com>
Fri, 6 Feb 2015 23:57:52 +0000 (00:57 +0100)
tungre.cpp

index 82bfa347d636ce09ce98cc720d52cc406da1fcc4..9b93e8531bab246f761605de5a7d08a567a66558 100644 (file)
@@ -69,15 +69,21 @@ struct GREPacket {
        }
 };
 
-class Sender {
+class Protocol {
 public:
        virtual void send_packet(uint16_t proto, const string &data) = 0;
+       virtual int fd() const = 0;
 };
 
-class GRESender : public Sender {
+class Reorderer;
+class Protocol;
+
+class GREProtocol : public Protocol {
 public:
-       GRESender(int sock, const in6_addr &dst);
+       GREProtocol(const in6_addr &myaddr, const in6_addr &dst);
        virtual void send_packet(uint16_t proto, const string &data);
+       virtual int fd() const;
+       void read_packet(Reorderer* sender);
 
 private:
        int seq;
@@ -85,10 +91,12 @@ private:
        sockaddr_in6 dstaddr;
 };
 
-class TUNSender : public Sender {
+class TUNProtocol : public Protocol {
 public:
-       TUNSender(int tunfd);
+       TUNProtocol(const char *devname);
        virtual void send_packet(uint16_t proto, const string &data);
+       virtual int fd() const;
+       void read_packet(Protocol* sender);
 
 private:
        int tunfd;
@@ -96,28 +104,43 @@ private:
 
 class Reorderer {
 public:
-       Reorderer(Sender* sender);
+       Reorderer(Protocol* sender);
        void handle_packet(uint16_t proto, const string& data, int seq);
 
 private:
        void send_packet(uint16_t proto, const string &data, bool silence);
 
-       Sender* sender;
+       Protocol* sender;
        int last_seq;
 
        priority_queue<GREPacket, vector<GREPacket>, greater<GREPacket>> packet_buffer;
        map<int, int> ccs;
 };
 
-GRESender::GRESender(int sock, const in6_addr &dst)
-       : sock(sock), seq(0)
+GREProtocol::GREProtocol(const in6_addr &src, const in6_addr &dst)
+       : seq(0)
 {
        memset(&dstaddr, 0, sizeof(dstaddr));
        dstaddr.sin6_family = AF_INET6;
        dstaddr.sin6_addr = dst;
+
+       sock = socket(AF_INET6, SOCK_RAW, IPPROTO_GRE);
+       if (sock == -1) {
+               perror("socket");
+               exit(1);
+       }
+
+       sockaddr_in6 my_addr;
+       memset(&my_addr, 0, sizeof(my_addr));
+       my_addr.sin6_family = AF_INET6;
+       my_addr.sin6_addr = src;
+       if (bind(sock, (sockaddr *)&my_addr, sizeof(my_addr)) == -1) {
+               perror("bind");
+               exit(1);
+       }
 }
 
-void GRESender::send_packet(uint16_t proto, const string &data)
+void GREProtocol::send_packet(uint16_t proto, const string &data)
 {
        char buf[4096];
        gre_header *gre = (gre_header *)buf;
@@ -139,11 +162,17 @@ void GRESender::send_packet(uint16_t proto, const string &data)
                return;
        }
 }
+
+int GREProtocol::fd() const
+{
+       return sock;
+}
        
-TUNSender::TUNSender(int tunfd)
-       : tunfd(tunfd) {}
+TUNProtocol::TUNProtocol(const char *devname)
+       : tunfd(tun_open(devname)) {
+}
 
-void TUNSender::send_packet(uint16_t proto, const string &data)
+void TUNProtocol::send_packet(uint16_t proto, const string &data)
 {
        char buf[4096];
 
@@ -165,7 +194,12 @@ void TUNSender::send_packet(uint16_t proto, const string &data)
        }
 }
 
-Reorderer::Reorderer(Sender* sender)
+int TUNProtocol::fd() const
+{
+       return tunfd;
+}
+
+Reorderer::Reorderer(Protocol* sender)
        : sender(sender), last_seq(-1)
 {
 }
@@ -237,12 +271,12 @@ void Reorderer::send_packet(uint16_t proto, const string &data, bool silence)
        sender->send_packet(proto, data);
 }
 
-void read_gre_packet(int gresock, const in6_addr &remoteaddr, Reorderer *sender)
+void GREProtocol::read_packet(Reorderer *sender)
 {
        struct sockaddr_storage addr;
        socklen_t addrlen = sizeof(addr);
        char buf[4096];
-       int ret = recvfrom(gresock, buf, sizeof(buf), 0, (struct sockaddr *)&addr, &addrlen);
+       int ret = recvfrom(sock, buf, sizeof(buf), 0, (struct sockaddr *)&addr, &addrlen);
        if (ret == -1) {
                perror("recvfrom");
                exit(1);
@@ -251,7 +285,7 @@ void read_gre_packet(int gresock, const in6_addr &remoteaddr, Reorderer *sender)
                return;
        }
        struct in6_addr *addr6 = &((struct sockaddr_in6 *)&addr)->sin6_addr;
-       if (memcmp(addr6, &remoteaddr, sizeof(*addr6)) != 0) {
+       if (memcmp(addr6, &dstaddr.sin6_addr, sizeof(*addr6)) != 0) {
                // ignore
                return;
        }
@@ -275,7 +309,7 @@ void read_gre_packet(int gresock, const in6_addr &remoteaddr, Reorderer *sender)
        sender->handle_packet(ntohs(gre->protocol_type), string(ptr, buf + ret), seq);
 }
 
-void read_tun_packet(int tunfd, Sender *sender)
+void TUNProtocol::read_packet(Protocol *sender)
 {
        char buf[4096];
        int ret = read(tunfd, buf, sizeof(buf));
@@ -300,44 +334,29 @@ void read_tun_packet(int tunfd, Sender *sender)
 
 int main(int argc, char **argv)
 {
-       int tunfd = tun_open("tungre");
-       int gresock = socket(AF_INET6, SOCK_RAW, IPPROTO_GRE);
-       if (gresock == -1) {
-               perror("socket");
-               exit(1);
-       }
-
-       sockaddr_in6 my_addr;
-       memset(&my_addr, 0, sizeof(my_addr));
-       my_addr.sin6_family = AF_INET6;
-       my_addr.sin6_addr = get_addr(argv[1]);
-       if (bind(gresock, (sockaddr *)&my_addr, sizeof(my_addr)) == -1) {
-               perror("bind");
-               exit(1);
-       }
-
+       in6_addr myaddr = get_addr(argv[1]);
        in6_addr remoteaddr = get_addr(argv[2]);
-       GRESender gre_sender(gresock, remoteaddr);
-       TUNSender tun_sender(tunfd);
+       GREProtocol gre(myaddr, remoteaddr);
+       TUNProtocol tun("tungre");
 
-       Reorderer tun_reorderer(&tun_sender);
+       Reorderer tun_reorderer(&tun);
 
        fd_set fds;
        FD_ZERO(&fds);
        for ( ;; ) {
-               FD_SET(gresock, &fds);
-               FD_SET(tunfd, &fds);
+               FD_SET(gre.fd(), &fds);
+               FD_SET(tun.fd(), &fds);
                int ret = select(1024, &fds, NULL, NULL, NULL);
                if (ret == -1) {
                        perror("select");
                        continue;
                }
 
-               if (FD_ISSET(gresock, &fds)) {
-                       read_gre_packet(gresock, remoteaddr, &tun_reorderer);
+               if (FD_ISSET(gre.fd(), &fds)) {
+                       gre.read_packet(&tun_reorderer);
                }
-               if (FD_ISSET(tunfd, &fds)) {
-                       read_tun_packet(tunfd, &gre_sender);
+               if (FD_ISSET(tun.fd(), &fds)) {
+                       tun.read_packet(&gre);
                }
        }
 }