PPTServer.cc
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #include <config.h>
00034
00035 #include <string>
00036 #include <sstream>
00037 #include <cstdlib>
00038
00039 using std::string ;
00040 using std::ostringstream ;
00041
00042 #include "PPTServer.h"
00043 #include "BESInternalError.h"
00044 #include "BESSyntaxUserError.h"
00045 #include "PPTProtocol.h"
00046 #include "SocketListener.h"
00047 #include "ServerHandler.h"
00048 #include "Socket.h"
00049 #include "TheBESKeys.h"
00050 #include "BESDebug.h"
00051
00052 #include "config.h"
00053 #ifdef HAVE_OPENSSL
00054 #include "SSLServer.h"
00055 #endif
00056
00057 #define PPT_SERVER_DEFAULT_TIMEOUT 1
00058
00059 PPTServer::PPTServer( ServerHandler *handler,
00060 SocketListener *listener,
00061 bool isSecure )
00062 : PPTConnection( PPT_SERVER_DEFAULT_TIMEOUT),
00063 _handler( handler ),
00064 _listener( listener ),
00065 _secure( isSecure )
00066 {
00067 if( !handler )
00068 {
00069 string err( "Null handler passed to PPTServer" ) ;
00070 throw BESInternalError( err, __FILE__, __LINE__ ) ;
00071 }
00072 if( !listener )
00073 {
00074 string err( "Null listener passed to PPTServer" ) ;
00075 throw BESInternalError( err, __FILE__, __LINE__ ) ;
00076 }
00077 #ifndef HAVE_OPENSSL
00078 if( _secure )
00079 {
00080 string err("Server requested to be secure but OpenSSL is not built in");
00081 throw BESInternalError( err, __FILE__, __LINE__ ) ;
00082 }
00083 #endif
00084
00085
00086 if( _secure )
00087 {
00088 get_secure_files() ;
00089 }
00090 }
00091
00092 PPTServer::~PPTServer()
00093 {
00094 }
00095
00096 void
00097 PPTServer::get_secure_files()
00098 {
00099 bool found = false ;
00100 TheBESKeys::TheKeys()->get_value( "BES.ServerCertFile", _cfile, found ) ;
00101 if( !found || _cfile.empty() )
00102 {
00103 string err = "Unable to determine server certificate file." ;
00104 throw BESSyntaxUserError( err, __FILE__, __LINE__ ) ;
00105 }
00106
00107 found = false ;
00108 TheBESKeys::TheKeys()->get_value( "BES.ServerCertAuthFile", _cafile, found);
00109 if( !found || _cafile.empty() )
00110 {
00111 string err = "Unable to determine server certificate authority file." ;
00112 throw BESSyntaxUserError( err, __FILE__, __LINE__ ) ;
00113 }
00114
00115 found = false ;
00116 TheBESKeys::TheKeys()->get_value( "BES.ServerKeyFile", _kfile, found ) ;
00117 if( !found || _kfile.empty() )
00118 {
00119 string err = "Unable to determine server key file." ;
00120 throw BESSyntaxUserError( err, __FILE__, __LINE__ ) ;
00121 }
00122
00123 found = false ;
00124 string portstr ;
00125 TheBESKeys::TheKeys()->get_value( "BES.ServerSecurePort", portstr, found ) ;
00126 if( !found || portstr.empty() )
00127 {
00128 string err = "Unable to determine secure connection port." ;
00129 throw BESSyntaxUserError( err, __FILE__, __LINE__ ) ;
00130 }
00131 _securePort = atoi( portstr.c_str() ) ;
00132 if( !_securePort )
00133 {
00134 string err = (string)"Unable to determine secure connection port "
00135 + "from string " + portstr ;
00136 throw BESSyntaxUserError( err, __FILE__, __LINE__ ) ;
00137 }
00138 }
00139
00145 void
00146 PPTServer::initConnection()
00147 {
00148 for(;;)
00149 {
00150 _mySock = _listener->accept() ;
00151 if( _mySock )
00152 {
00153 if( _mySock->allowConnection() == true )
00154 {
00155
00156 if( welcomeClient( ) != -1 )
00157 {
00158
00159 _handler->handle( this ) ;
00160 }
00161 }
00162 else
00163 {
00164 _mySock->close();
00165 }
00166 }
00167 }
00168 }
00169
00170 void
00171 PPTServer::closeConnection()
00172 {
00173 if( _mySock ) _mySock->close() ;
00174 }
00175
00176 int
00177 PPTServer::welcomeClient()
00178 {
00179
00180
00181
00182
00183
00184
00185 unsigned int ppt_buffer_size = 64 ;
00186 char *inBuff = new char[ppt_buffer_size+1] ;
00187 int bytesRead = readBufferNonBlocking( inBuff, ppt_buffer_size ) ;
00188
00189
00190 if( bytesRead == -1 )
00191 {
00192 _mySock->close() ;
00193 delete [] inBuff ;
00194 return -1 ;
00195 }
00196
00197 string status( inBuff, bytesRead ) ;
00198 delete [] inBuff ;
00199
00200 if( status != PPTProtocol::PPTCLIENT_TESTING_CONNECTION )
00201 {
00202
00203
00204
00205
00206 string err( "PPT cannot negotiate, " ) ;
00207 err += " client started the connection with " + status ;
00208 BESDEBUG( "ppt", err << endl ) ;
00209
00210 send( err ) ;
00211 _mySock->close() ;
00212 return -1 ;
00213 }
00214
00215 if( !_secure )
00216 {
00217 send( PPTProtocol::PPTSERVER_CONNECTION_OK ) ;
00218 }
00219 else
00220 {
00221 authenticateClient() ;
00222 }
00223
00224 return 0 ;
00225 }
00226
00227 void
00228 PPTServer::authenticateClient()
00229 {
00230 #ifdef HAVE_OPENSSL
00231 BESDEBUG( "ppt", "requiring secure connection: port = "
00232 << _securePort << endl ) ;
00233
00234 send( PPTProtocol::PPTSERVER_AUTHENTICATE ) ;
00235
00236
00237
00238
00239 unsigned int ppt_buffer_size = 64 ;
00240 char *inBuff = new char[ppt_buffer_size] ;
00241 int bytesRead = _mySock->receive( inBuff, ppt_buffer_size ) ;
00242 string portRequest( inBuff, bytesRead ) ;
00243 delete [] inBuff ;
00244 if( portRequest != PPTProtocol::PPTCLIENT_REQUEST_AUTHPORT )
00245 {
00246 string err( "Secure connection ... expecting request for port" ) ;
00247 err += " client requested " + portRequest ;
00248 throw BESInternalError( err, __FILE__, __LINE__ ) ;
00249 }
00250
00251
00252 ostringstream portResponse ;
00253 portResponse << _securePort << PPTProtocol::PPT_COMPLETE_DATA_TRANSMITION ;
00254 send( portResponse.str() ) ;
00255
00256
00257 SSLServer server( _securePort, _cfile, _cafile, _kfile ) ;
00258 server.initConnection() ;
00259 server.closeConnection() ;
00260
00261
00262
00263 #else
00264 string err = (string)"Authentication requested for this server "
00265 + "but OpenSSL is not built into the server" ;
00266 throw BESInternalError( err, __FILE__, __LINE__ ) ;
00267 #endif
00268 }
00269
00276 void
00277 PPTServer::dump( ostream &strm ) const
00278 {
00279 strm << BESIndent::LMarg << "PPTServer::dump - ("
00280 << (void *)this << ")" << endl ;
00281 BESIndent::Indent() ;
00282 if( _handler )
00283 {
00284 strm << BESIndent::LMarg << "server handler:" << endl ;
00285 BESIndent::Indent() ;
00286 _handler->dump( strm ) ;
00287 BESIndent::UnIndent() ;
00288 }
00289 else
00290 {
00291 strm << BESIndent::LMarg << "server handler: null" << endl ;
00292 }
00293 if( _listener )
00294 {
00295 strm << BESIndent::LMarg << "listener:" << endl ;
00296 BESIndent::Indent() ;
00297 _listener->dump( strm ) ;
00298 BESIndent::UnIndent() ;
00299 }
00300 else
00301 {
00302 strm << BESIndent::LMarg << "listener: null" << endl ;
00303 }
00304 strm << BESIndent::LMarg << "secure? " << _secure << endl ;
00305 if( _secure )
00306 {
00307 BESIndent::Indent() ;
00308 strm << BESIndent::LMarg << "cert file: " << _cfile << endl ;
00309 strm << BESIndent::LMarg << "cert authority file: " << _cafile << endl ;
00310 strm << BESIndent::LMarg << "key file: " << _kfile << endl ;
00311 strm << BESIndent::LMarg << "secure port: " << _securePort << endl ;
00312 BESIndent::UnIndent() ;
00313 }
00314 PPTConnection::dump( strm ) ;
00315 BESIndent::UnIndent() ;
00316 }
00317