Jelajahi Sumber

Fehler im Websocketprotokoll bei unvorhergesehenem verbindungsverlust behoben

Kolja Strohm 5 tahun lalu
induk
melakukan
7b0f2ac036
2 mengubah file dengan 42 tambahan dan 41 penghapusan
  1. 0 19
      Network/HttpRequest.cpp
  2. 42 22
      Network/WebSocket.cpp

+ 0 - 19
Network/HttpRequest.cpp

@@ -20,8 +20,6 @@ PostRequest::PostRequest( const char *path, const char *host, const char *data,
 
 Answer *PostRequest::execute() const
 {
-    ZeitMesser zm;
-    zm.messungStart();
     Text message = "POST ";
     message += path;
     message += " HTTP/1.1\r\n";
@@ -33,19 +31,10 @@ Answer *PostRequest::execute() const
     message += data.getLength();
     message += "\r\n\r\n";
     message += data;
-    zm.messungEnde();
-    std::cout << "http request string erstellen: " << zm.getSekunden() << "\n";
-    zm.messungStart();
     Klient httpK;
     if( !httpK.verbinde( port, host ) )
         return 0;
-    zm.messungEnde();
-    std::cout << "verbindung erstellen: " << zm.getSekunden() << "\n";
-    zm.messungStart();
     httpK.sende( message, message.getLength() );
-    zm.messungEnde();
-    std::cout << "request senden: " << zm.getSekunden() << "\n";
-    zm.messungStart();
     int length = -1;
     bool lastn = 0;
     Text answer;
@@ -54,12 +43,6 @@ Answer *PostRequest::execute() const
         buff[ 1 ] = 0;
         if( httpK.getNachricht( buff, 1 ) )
         {
-            if( !answer.getText() || !answer.getText()[ 0 ] )
-            {
-                zm.messungEnde();
-                std::cout << "auf antwort warten: " << zm.getSekunden() << "\n";
-                zm.messungStart();
-            }
             answer += buff;
             if( buff[ 0 ] == '\n' )
             {
@@ -94,8 +77,6 @@ Answer *PostRequest::execute() const
         else
             break;
     } while( httpK.hatNachricht( 1000 ) );
-    zm.messungEnde();
-    std::cout << "nachricht empfangen: " << zm.getSekunden() << "\n";
     return new Answer( answer );
 }
 

+ 42 - 22
Network/WebSocket.cpp

@@ -12,11 +12,21 @@ __declspec( dllexport ) Frame &Frame::operator+=( const Frame &b ) // baut frame
     if( opcode == 0 )
         opcode = b.opcode;
     dataLength += b.dataLength;
-    char *data = new char[ dataLength ];
-    memcpy( data, this->data, dataLength - b.dataLength );
-    memcpy( data + dataLength, b.data, b.dataLength );
-    delete[] this->data;
-    this->data = data;
+    if( dataLength )
+    {
+        char *data = new char[ dataLength ];
+        if( data )
+            memcpy( data, this->data, dataLength - b.dataLength );
+        if( b.data )
+            memcpy( data + dataLength, b.data, b.dataLength );
+        delete[] this->data;
+        this->data = data;
+    }
+    else
+    {
+        delete[] this->data;
+        this->data = 0;
+    }
     return *this;
 }
 
@@ -151,6 +161,7 @@ __declspec( dllexport ) void WebSocketClient::thread()
         }
         if( klient->hatNachricht( 100 ) )
         {
+            bool ok = 1;
             c2.unlock();
             bool first = 1;
             Frame m;
@@ -164,58 +175,60 @@ __declspec( dllexport ) void WebSocketClient::thread()
                     return;
                 }
                 Frame message;
-                klient->getNachricht( (char*)&byte, 1 );
+                ok &= klient->getNachricht( (char*)&byte, 1 );
                 message.fin = ( byte & 0x80 ) != 0;
                 message.rsv1 = ( byte & 0x40 ) != 0;
                 message.rsv2 = ( byte & 0x20 ) != 0;
                 message.rsv3 = ( byte & 0x10 ) != 0;
                 message.opcode = byte & 0xF;
-                klient->getNachricht( (char*)&byte, 1 );
+                ok &= klient->getNachricht( (char*)&byte, 1 );
                 message.mask = ( byte & 0x80 ) != 0;
                 message.dataLength = byte & 0x7F;
                 if( message.dataLength == 126 )
                 {
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength = byte << 8;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= byte;
                 }
                 else if( message.dataLength == 127 )
                 {
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength = (__int64)byte << 56;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte << 48;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte << 40;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte << 32;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte << 24;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte << 16;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte << 8;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.dataLength |= (__int64)byte;
                 }
                 if( message.mask )
                 {
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.key[ 0 ] = byte;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.key[ 1 ] = byte;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.key[ 2 ] = byte;
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     message.key[ 3 ] = byte;
                 }
+                if( !ok )
+                    message.dataLength = 1;
                 message.data = 0;
                 if( message.dataLength )
                     message.data = new char[ message.dataLength ];
                 for( int i = 0; i < message.dataLength; i++ )
                 {
-                    klient->getNachricht( (char*)&byte, 1 );
+                    ok &= klient->getNachricht( (char*)&byte, 1 );
                     if( message.mask )
                         message.data[ i ] = byte ^ message.key[ i % 4 ];
                     else
@@ -230,7 +243,14 @@ __declspec( dllexport ) void WebSocketClient::thread()
                     delete[] message.data;
                 }
                 first = 0;
+                if( !ok )
+                    break;
             } while( !m.fin );
+            if( !ok )
+            {
+                delete[] m.data;
+                return;
+            }
             if( m.opcode == 0x9 )
             {
                 m.opcode = 0xA;