#include "../KSGKlient.h" #include "../KSGServer.h" #include #include "../Keys.h" #include // Inhalt der NewsKlients Klasse aus KSGKlient.h // Konstruktor NewsKlient::NewsKlient() { verbunden = 0; klient = 0; fehler = new Text( "" ); klientId = getKlientId(); ref = 1; } // Destruktor NewsKlient::~NewsKlient() { cs.lock(); if( klient ) { char serverReturn = 0; if( verbunden ) { klient->sendeEncrypted( "\4", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); if( serverReturn == 3 ) { char län = 0; klient->getNachrichtEncrypted( &län, 1 ); char *nachricht = new char[ län + 1 ]; nachricht[ län ] = 0; klient->getNachrichtEncrypted( nachricht, län ); delete[]nachricht; } klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); } else { int keyLen = 0; char *key = 0; Keys::getServerKey( &key, keyLen, Keys::NEWS, Keys::SENDEN ); klient->setSendeKey( key, keyLen ); delete[] key; Keys::getServerKey( &key, keyLen, Keys::NEWS, Keys::EMPFANGEN ); klient->setEmpfangKey( key, keyLen ); delete[] key; klient->verbinde( klient->getServerPort(), klient->getServerIp() ); klient->sendeEncrypted( "\1", 1 ); klient->sendeEncrypted( (char*)&klientId, 4 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); if( serverReturn == 3 ) { char län = 0; klient->getNachrichtEncrypted( &län, 1 ); char *nachricht = new char[ län + 1 ]; nachricht[ län ] = 0; klient->getNachrichtEncrypted( nachricht, län ); delete[]nachricht; } else { char *sl = 0; char slLän = getSchlüssel( &sl ); klient->setSendeKey( sl, slLän ); klient->setEmpfangKey( sl, slLän ); delete[] sl; klient->sendeEncrypted( "\4", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); if( serverReturn == 3 ) { char län = 0; klient->getNachrichtEncrypted( &län, 1 ); char *nachricht = new char[ län + 1 ]; nachricht[ län ] = 0; klient->getNachrichtEncrypted( nachricht, län ); delete[]nachricht; } } klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); } klient = klient->release(); } fehler = fehler->release(); cs.unlock(); } // nicht constant bool NewsKlient::verbinde() // verbindet ich mit dem News Server { cs.lock(); if( verbunden ) { cs.unlock(); return 1; } if( !klient ) { char *msIp = getMainServerIp(); unsigned short msPort = getMainServerPort(); Framework::logLine( "Verbinung mit Main Server wird hergestellt..." ); klient = new Klient(); int keyLen = 0; char *key = 0; Keys::getServerKey( &key, keyLen, Keys::MAIN, Keys::SENDEN ); klient->setSendeKey( key, keyLen ); delete[] key; Keys::getServerKey( &key, keyLen, Keys::MAIN, Keys::EMPFANGEN ); klient->setEmpfangKey( key, keyLen ); delete[] key; if( !klient->verbinde( msPort, msIp ) ) { Framework::logLine( "ERROR: Server nicht erreichbar." ); fehler->setText( "Fehler beim verbinden mit dem Main Server. Bitte versuche es Später erneut." ); klient = klient->release(); delete[]msIp; cs.unlock(); return 0; } delete[]msIp; klient->sende( "\0", 1 ); // Verschlüsselung aktivieren klient->sendeEncrypted( "\1", 1 ); klient->sendeEncrypted( (char*)&klientId, 4 ); char serverReturn = 0; klient->getNachrichtEncrypted( &serverReturn, 1 ); if( serverReturn == 3 ) { char län = 0; klient->getNachrichtEncrypted( &län, 1 ); char *nachricht = new char[ län + 1 ]; nachricht[ län ] = 0; klient->getNachrichtEncrypted( nachricht, län ); Framework::logLine( Text( "ERROR: " ) += nachricht ); fehler->setText( nachricht ); delete[]nachricht; klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); klient = klient->release(); cs.unlock(); return 0; } char *sl = 0; char slLän = getSchlüssel( &sl ); klient->setSendeKey( sl, slLän ); klient->setEmpfangKey( sl, slLän ); delete[] sl; klient->sendeEncrypted( "\6\x9", 2 ); char byte = 0; klient->getNachrichtEncrypted( &byte, 1 ); if( byte == 2 ) { unsigned char lsIp[ 4 ]; klient->getNachrichtEncrypted( (char *)lsIp, 4 ); unsigned short lsPort = 0; klient->getNachrichtEncrypted( (char*)&lsPort, 2 ); klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); Text *lsIpT = new Text( "" ); lsIpT->append( (int)lsIp[ 0 ] ); lsIpT->append( "." ); lsIpT->append( (int)lsIp[ 1 ] ); lsIpT->append( "." ); lsIpT->append( (int)lsIp[ 2 ] ); lsIpT->append( "." ); lsIpT->append( (int)lsIp[ 3 ] ); Framework::logLine( ( ( Text( "Zugeteilter News Server:" ) += lsIpT->getText() ) += ":" ) += lsPort ); int keyLen = 0; char *key = 0; Keys::getServerKey( &key, keyLen, Keys::NEWS, Keys::SENDEN ); klient->setSendeKey( key, keyLen ); delete[] key; Keys::getServerKey( &key, keyLen, Keys::NEWS, Keys::EMPFANGEN ); klient->setEmpfangKey( key, keyLen ); delete[] key; klient->verbinde( lsPort, lsIpT->getText() ); lsIpT = lsIpT->release(); klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); } if( byte == 3 ) { klient->getNachrichtEncrypted( &byte, 1 ); char *f = new char[ byte + 1 ]; f[ byte ] = 0; klient->getNachrichtEncrypted( f, byte ); Framework::logLine( Text( "ERROR: " ) += f ); fehler->setText( f ); delete[]f; klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); klient = klient->release(); cs.unlock(); return 0; } } Framework::logLine( "Verbinung mit News Server wird hergestellt..." ); int keyLen = 0; char *key = 0; Keys::getServerKey( &key, keyLen, Keys::NEWS, Keys::SENDEN ); klient->setSendeKey( key, keyLen ); delete[] key; Keys::getServerKey( &key, keyLen, Keys::NEWS, Keys::EMPFANGEN ); klient->setEmpfangKey( key, keyLen ); delete[] key; if( klient->verbinde( klient->getServerPort(), klient->getServerIp() ) ) { if( klient->sendeEncrypted( "\1", 1 ) ) { klient->sendeEncrypted( (char*)&klientId, 4 ); char serverReturn = 0; klient->getNachrichtEncrypted( &serverReturn, 1 ); if( serverReturn == 3 ) { char byte = 0; klient->getNachrichtEncrypted( &byte, 1 ); char *f = new char[ byte + 1 ]; f[ byte ] = 0; klient->getNachrichtEncrypted( f, byte ); fehler->setText( f ); Framework::logLine( Text( "ERROR: " ) += f ); delete[]f; klient->sendeEncrypted( "\3", 1 ); klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); cs.unlock(); return 0; } char *sl = 0; char slLän = getSchlüssel( &sl ); klient->setSendeKey( sl, slLän ); klient->setEmpfangKey( sl, slLän ); delete[] sl; verbunden = 1; cs.unlock(); Framework::logLine( "Erfolgreich mit News Server verbunden." ); return 1; } else { Framework::logLine( "ERROR: Senden zum Server nicht erfolgreich." ); fehler->setText( "Der dir zugewiesene News Server hat die Verbindung abgebrochen. Bitte versuche es Später erneut." ); klient = klient->release(); } } else { Framework::logLine( "ERROR: Server nicht erreichbar." ); fehler->setText( "Der dir zugewiesene News Server antwortet nicht. Bitte versuche es Später erneut." ); klient = klient->release(); } cs.unlock(); return 0; } bool NewsKlient::ladeSeite( char *name ) { cs.lock(); if( !verbunden ) verbinde(); if( !verbunden ) { cs.unlock(); return 0; } klient->sendeEncrypted( "\5", 1 ); char ret = 0; klient->getNachrichtEncrypted( &ret, 1 ); if( ret == 1 ) { char län = (char)textLength( name ); klient->sendeEncrypted( &län, 1 ); klient->sendeEncrypted( name, län ); klient->getNachrichtEncrypted( &ret, 1 ); if( ret == 1 ) { Text *pfad = new Text( "data/tmp/news/" ); pfad->append( name ); if( DateiExistiert( pfad->getThis() ) ) DateiRemove( pfad->getThis() ); pfad->append( "/" ); int dAnz = 0; klient->getNachrichtEncrypted( (char*)&dAnz, 4 ); for( int i = 0; i < dAnz; i++ ) { char nLän = 0; klient->getNachrichtEncrypted( &nLän, 1 ); char *dName = new char[ nLän + 1 ]; dName[ nLän ] = 0; klient->getNachrichtEncrypted( dName, nLän ); Text *pf = new Text( pfad->getText() ); pf->append( dName ); delete[] dName; Datei *d = new Datei(); d->setDatei( pf ); d->erstellen(); d->open( Datei::Style::schreiben ); __int64 dGr = 0; klient->getNachrichtEncrypted( (char*)&dGr, 8 ); char buffer[ 2048 ]; while( dGr > 0 ) { int län = dGr > 2048 ? 2048 : (int)dGr; klient->getNachricht( buffer, län ); d->schreibe( buffer, län ); dGr -= län; } d->close(); d->release(); } pfad->release(); } } if( ret == 3 ) { klient->getNachrichtEncrypted( &ret, 1 ); if( ret ) { char *tmp = new char[ ret ]; klient->getNachrichtEncrypted( tmp, ret ); delete[] tmp; } cs.unlock(); return 0; } cs.unlock(); return 1; } bool NewsKlient::keepAlive() // Erhält die Verbindung aufrecht { if( !verbunden ) return 0; char res = 0; if( !cs.tryLock() ) return 1; Framework::logLine( "Verbindungstest zum News Server..." ); bool ok = klient->sendeEncrypted( "\x6", 1 ); ok &= klient->getNachrichtEncrypted( &res, 1 ); cs.unlock(); if( res != 1 || !ok ) { Framework::logLine( "Verbindungsabbruch." ); trenne(); } else Framework::logLine( "Verbindung besteht." ); return res == 1; } bool NewsKlient::trenne() // trennt sich von dem News Server { if( !verbunden ) return 1; cs.lock(); Framework::logLine( "Verbindung zum News Server wird getrennt..." ); klient->sendeEncrypted( "\3", 1 ); char serverReturn = 0; klient->getNachrichtEncrypted( &serverReturn, 1 ); klient->trenne(); verbunden = 0; cs.unlock(); return 1; } // constant bool NewsKlient::istVerbunden() const // prüft, ob mit News Server verbunden { return verbunden; } char *NewsKlient::getLetzterFehler() const // gibt den Letzten Fehlertext zuück { return fehler->getText(); } // Reference Counting NewsKlient *NewsKlient::getThis() { ref++; return this; } NewsKlient *NewsKlient::release() { ref--; if( !ref ) delete this; return 0; }