winsock (redirection, aka. bounce)



  • ich will eine art proxy schreiben der
    so funzt

    192.168.0.98 --------------->192.168.0.113--------------> 192.168.0.99
    connected connected
    port 12345 port 21

    also alle anfragen werden über host 192.168.0.113 geleitet, hin und zurück
    also ein proxy halt ;=)
    nur mein prob ist das ich einen befehl von 192.168.0.98 sende muss ich 3 oder 4 mal enter drücken damit ich eine antwort bekomme von 192.168.0.99, also alles ist zeit versetz, es kommt immer ein paar zyklen zuspät ick wes aber net wieso ??
    danke für euere hilfe

    #include <windows.h>
    #include <winsock.h>
    #include <stdio.h>
    #include <io.h>
    #include <stdlib.h>
    
    //Prototypen
    int startWinsock(void);
    
    int main()
    {
      int old;
        long rc;
      SOCKET acceptSocket;
      SOCKET connectedSocket;
      SOCKADDR_IN addr;
      char buf[256];
      char buf2[300];
        char   psBuffer[128];
       FILE   *pPipe;
    
    //HideWindow("adsf.exe",1);
    
      // Winsock starten
      rc=startWinsock();
      if(rc!=0)
      {
        printf("Fehler: startWinsock, fehler code: %d\n",rc);
        return 1;
      }
      else
      {
        printf("Winsock gestartet!\n");
      }
    
      // Socket erstellen
      acceptSocket=socket(AF_INET,SOCK_STREAM,0);
      if(acceptSocket==INVALID_SOCKET)
      {
        printf("Fehler: Der Socket konnte nicht erstellt werden, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Socket erstellt!\n");
      }
    
      // Socket binden
      memset(&addr,0,sizeof(SOCKADDR_IN));
      addr.sin_family=AF_INET;
      addr.sin_port=htons(12345);
      addr.sin_addr.s_addr=inet_addr("192.168.0.113");
      rc=bind(acceptSocket,(SOCKADDR*)&addr,sizeof(SOCKADDR_IN));
      if(rc==SOCKET_ERROR)
      {
        printf("Fehler: bind, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Socket an port 12345 gebunden\n");
      }
    
      // In den listen Modus
      rc=listen(acceptSocket,10);
      if(rc==SOCKET_ERROR)
      {
        printf("Fehler: listen, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("acceptSocket ist im listen Modus....\n");
      }
    
      // Verbindung annehmen
      connectedSocket=accept(acceptSocket,NULL,NULL);
    
      if(connectedSocket==INVALID_SOCKET)
      {
        printf("Fehler: accept, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Neue Verbindung wurde akzeptiert!\n");
      }
    
      // Daten austauschen
      while(rc!=SOCKET_ERROR)
      {
        rc=recv(connectedSocket,buf,256,0);
        if(rc==0)
       {
         printf("Server hat die Verbindung getrennt..\n");
          break;
        }
        if(rc==SOCKET_ERROR)
        {
          printf("Fehler: recv, fehler code: %d\n",WSAGetLastError());
          break;
        }
        buf[rc]='\0';
        //printf("Client sendet: %s\n",buf);
    
       if( (pPipe = _popen( buf, "rt" )) == NULL )
          exit( 1 );
    
       while( !feof( pPipe ) )
       {
          if( fgets( buf2, 128, pPipe ) != NULL )
        rc=send(connectedSocket,buf2,strlen(buf2),0);    
       }
    
      }
      closesocket(acceptSocket);
      closesocket(connectedSocket);
      WSACleanup();
      return 0;
    }
    
    int startWinsock(void)
    {
      WSADATA wsa;
      return WSAStartup(MAKEWORD(2,0),&wsa);
    }
    


  • scheisse ich habe den falschen code gepostet jetzt aber

    #include <windows.h>
    #include <winsock.h>
    #include <stdio.h>
    #include <io.h>
    #include <stdlib.h>
    
    //Prototypen
    int startWinsock(void);
    
    int main()
    {
      int old;
        long rc;
        long rc2,s;
      SOCKET acceptSocket;
      SOCKET connectedSocket;
      SOCKADDR_IN addr;
      char buf [256];
      char buf2[256];
    
      // Winsock starten
      rc=startWinsock();
      if(rc!=0)
      {
        printf("Fehler: startWinsock, fehler code: %d\n",rc);
        return 1;
      }
      else
      {
        printf("Winsock gestartet!\n");
      }
    
      // Socket erstellen
      acceptSocket=socket(AF_INET,SOCK_STREAM,0);
      if(acceptSocket==INVALID_SOCKET)
      {
        printf("Fehler: Der Socket konnte nicht erstellt werden, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Socket erstellt!\n");
      }
    
        s=socket(AF_INET,SOCK_STREAM,0);
      if(s==INVALID_SOCKET)
      {
        printf("Fehler: Der Socket konnte nicht erstellt werden, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Socket erstellt!\n");
      }
    
      // Verbinden
      memset(&addr,0,sizeof(SOCKADDR_IN)); // zuerst alles auf 0 setzten
      addr.sin_family=AF_INET;
      addr.sin_port=htons(21); // wir verwenden mal port 12345
      addr.sin_addr.s_addr=inet_addr("192.168.0.99"); // zielrechner ist unser eigener
    
      rc2=connect(s,(SOCKADDR*)&addr,sizeof(SOCKADDR));
      if(rc2==SOCKET_ERROR)
      {
        printf("Fehler: connect gescheitert, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Verbunden mit 127.0.0.1..\n");
      }
    
      // Socket binden
      memset(&addr,0,sizeof(SOCKADDR_IN));
      addr.sin_family=AF_INET;
      addr.sin_port=htons(12345);
      addr.sin_addr.s_addr=inet_addr("192.168.0.113");
      rc=bind(acceptSocket,(SOCKADDR*)&addr,sizeof(SOCKADDR_IN));
      if(rc==SOCKET_ERROR)
      {
        printf("Fehler: bind, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Socket an port 12345 gebunden\n");
      }
    
      // In den listen Modus
      rc=listen(acceptSocket,10);
      if(rc==SOCKET_ERROR)
      {
        printf("Fehler: listen, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("acceptSocket ist im listen Modus....\n");
      }
    
      // Verbindung annehmen
      connectedSocket=accept(acceptSocket,NULL,NULL);
    
      if(connectedSocket==INVALID_SOCKET)
      {
        printf("Fehler: accept, fehler code: %d\n",WSAGetLastError());
        return 1;
      }
      else
      {
        printf("Neue Verbindung wurde akzeptiert!\n");
      }
    
      // Daten austauschen
      while(rc!=SOCKET_ERROR)
      {
        rc=recv(connectedSocket,buf,256,0);
                                                    if(rc==0)
                                                   {
                                                     printf("Server hat die Verbindung getrennt..\n");
                                                      break;
                                                    }
    
                                                                    if(rc==SOCKET_ERROR)
                                                                    {
                                                                      printf("Fehler: recv, fehler code: %d\n",WSAGetLastError());
                                                                      break;
                                                                    }
        buf[rc]='\0';
    
       send(s,buf,strlen(buf),0);
    
       rc=recv(s,buf,256,0); 
    
       buf[rc]='\0';
    
       rc=send(connectedSocket,buf,strlen(buf),0);    
    
      }
      closesocket(acceptSocket);
      closesocket(connectedSocket);
      WSACleanup();
      return 0;
    }
    
    int startWinsock(void)
    {
      WSADATA wsa;
      return WSAStartup(MAKEWORD(2,0),&wsa);
    }
    


  • moment mal, willst du ip spoofen, oder nen richtigen proxie?
    wenn du nämlich ne andere absender ip machen willst, als du in wirklichkeit hast, musst du über raw sockets gehen!



  • ähhh WAS? lies mal mein posting , ich brauch doch da keinen raw socket !!!



  • also...
    grundsätzlich solltest du schon mal nicht deinen ganzen (wirren, unnützen) code posten, sondern nur teile auf dies ankommt.

    desweiteren versteh ich immer noch nicht ganz den eigentlichen ablauf des programmes. kann ich zusammenfassen:

    Client: 192.168.0.10 (z.b.)
    Server: 192.168.0.99
    Remotehost: 192.168.0.113
    
    Client       |      Server         |     Remotehost
    --------------------------------------------------
    verbindet -> |<-ist verbunden mit->|  <- ist verbunden
    

    so jetz mal n paar ideen die mir da spontan einfallen (die vielleicht nix mit der lösung deines probs zu tun haben):

    • wenn du jedes beliebige paket, dass bei server reinkommt weiterleiten willst, brauchst du raw sockets
    • in der while schleife würd ich das ganze über select laufen lassen, weil du nie weist, welcher der beiden partner jetz denn senden / empfangen will
    • dein problem mit dem "manchmal funktionieren" könnte sich auf obiges zurückführen lassen. dass das programm schwierigkeiten mit dem blockierenden aufrufen hat.

    ot: bitte entschuldige wenn das posting jetz etwas planlos is, es is fast halb 4 und ich hundemüde ^^



  • // Daten austauschen
      while(rc!=SOCKET_ERROR)
      {
    
        rc=recv(connectedSocket,buf,256,0);  
        buf[rc]='\0';
    
        send(s,buf,strlen(buf),0);
    
        rc2=recv(s,buf,256,0); 
    
       buf[rc2]='\0';
        rc=send(connectedSocket,buf,strlen(buf),0);    
    
      }
    

    Client | Server | Remotehost
    --------------------------------------------------
    verbindet -> |<-ist verbunden mit->| <- ist verbunden
    ^ ^
    | |
    | |
    connectedSocket s

    also der client connected zum server, sendet buf , der server ist mit dem s socket mit dem remotehost verbunden, und soll jetzt den buf über den s socket zu dem remotehost senden.

    und zurück gehts genauso

    wie mache ich jetzt das das der server weiß was zuerst ankommt, z.B
    ich connecte an einen ftp der sendet einen banner, ok ?
    also empfängt s als erstes und muss an connectedsocket weiter schicken.
    ümgekehrt gehts analog

    ich hoffe habe mich richtig ausgedrückt, bin nein bisserl fit mit sockets.



  • mit select kannst du mehrere sockets überwachen. in deinem fall überwachst du beim server den sockel zum client und zum remotehost. je nach dem wo daten reinkommen, schickst du sie entsprechend weiter. dann würd ich wiederum auch auf der client seite vielleicht mit threads arbeiten, damit du immer sowohl senden als auch empfangen kannst. für beispiele für select siehe google



  • @korbi

    kannst du mir ein beispiel sagen wie du das lösen würdest, habe jetzt 20 min gegoogelt aber nichts gefunden mit dem ein noob wie ich was anfangen könnte



  • jetz nen ganzen code zu posten wär n bisschen aufwändig und auch nicht zweckmässig 😃
    ich würd den server so aufbauen (etwas pseudo geschrieben, da ich die einzelnen funktionsaufrufe nicht genau im kopf hab):

    -> winsock initialisieren
    -> sockets: sock2remote, sock2client, serversock
    -> server starten:
       -> addressinfo machen
       -> socket erstellen
       -> socket an gewünschten port binden
       -> mit listen(1,...) auf einen client hören
    
       -> addressinfo (normalerweise macht man für jede verbindung ne eigene addr_in instanz)
       -> socket erstellen
    
    -> jetz warten, bis sich der client verbindet, am besten mit ca so:
       for (;;) // wir wollen ewig auf clients warten
       {
          sock2client = accept(...);
          clienthandler(); // muss nicht sein, ich hab das handling von nem client halt immer gern in ner eigenen funktion
       }
    
    -> in der clienthandler():
       -> sofort zum remotehost verbinden (erst jetz, weil du sonst wahrscheinlich n timeout vom remotehost kriegst)
       -> jetzt select routine starten:
       for (;;)
       {
           select(sock2remote, ...); // die aufrufe sind bisschen kompliziert, komme späternochmal darauf
           // jetz auf beiden sockeln lesen
           int ret1 = recv(sock2remote, ...);
           int ret2 = recv(sock2client, ...);
           // durch ret1 und ret2 herausfinden, auf welchem socket was reingekommen ist
           if (ret1) // weis nicht ob das so stimmt, jedenfalls wenn auf remote was reingekommen ist:
               send (sock2client, ...);
           if (ret2) // ...
           // es gibt auch noch timeout
       }
    

    ein gutes select beispiel (was sogar diesen proxieeffekt macht, glaub ich) findeste unter www.zotteljedi.de (die sockettips)



  • Hab es jetzt hinbekommen, würde mich über verbesserungsvorschläge freuen.
    hier is der code

    [url]http://www.delikon.de/codes/bounce.txt [/url]

    und vc++ workspace hier

    [url] http://www.delikon.de/zips/bouncer.zip [/url]
    danke für die hilfe korbi


Anmelden zum Antworten